Sophie

Sophie

distrib > Fedora > 14 > x86_64 > by-pkgid > 8d1ef08c9e0d44c69764afc615a03d0d > files > 1945

ghc-ghc-devel-6.12.3-5.fc14.i686.rpm

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
<head>
<!-- Generated by HsColour, http://www.cs.york.ac.uk/fp/darcs/hscolour/ -->
<title>typecheck/TcType.lhs</title>
<link type='text/css' rel='stylesheet' href='hscolour.css' />
</head>
<body>
%
% (c) The University of Glasgow 2006
% (c) The GRASP/AQUA Project, Glasgow University, 1992-1998
%
\section[TcType]{Types used in the typechecker}

This module provides the Type interface for front-end parts of the 
compiler.  These parts 

	* treat "source types" as opaque: 
		newtypes, and predicates are meaningful. 
	* look through usage types

The "tc" prefix is for "TypeChecker", because the type checker
is the principal client.

\begin{code}
<pre><a name="line-1"></a><span class='hs-keyword'>module</span> <span class='hs-conid'>TcType</span> <span class='hs-layout'>(</span>
<a name="line-2"></a>  <span class='hs-comment'>--------------------------------</span>
<a name="line-3"></a>  <span class='hs-comment'>-- Types </span>
<a name="line-4"></a>  <span class='hs-conid'>TcType</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcSigmaType</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcRhoType</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcTauType</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcPredType</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcThetaType</span><span class='hs-layout'>,</span> 
<a name="line-5"></a>  <span class='hs-conid'>TcTyVar</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcTyVarSet</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcKind</span><span class='hs-layout'>,</span> 
<a name="line-6"></a>
<a name="line-7"></a>  <span class='hs-conid'>BoxyTyVar</span><span class='hs-layout'>,</span> <span class='hs-conid'>BoxySigmaType</span><span class='hs-layout'>,</span> <span class='hs-conid'>BoxyRhoType</span><span class='hs-layout'>,</span> <span class='hs-conid'>BoxyThetaType</span><span class='hs-layout'>,</span> <span class='hs-conid'>BoxyType</span><span class='hs-layout'>,</span>
<a name="line-8"></a>
<a name="line-9"></a>  <span class='hs-comment'>--------------------------------</span>
<a name="line-10"></a>  <span class='hs-comment'>-- MetaDetails</span>
<a name="line-11"></a>  <span class='hs-conid'>UserTypeCtxt</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprUserTypeCtxt</span><span class='hs-layout'>,</span>
<a name="line-12"></a>  <span class='hs-conid'>TcTyVarDetails</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-conid'>BoxInfo</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprTcTyVarDetails</span><span class='hs-layout'>,</span>
<a name="line-13"></a>  <span class='hs-conid'>MetaDetails</span><span class='hs-layout'>(</span><span class='hs-conid'>Flexi</span><span class='hs-layout'>,</span> <span class='hs-conid'>Indirect</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-conid'>SkolemInfo</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprSkolTvBinding</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprSkolInfo</span><span class='hs-layout'>,</span>
<a name="line-14"></a>  <span class='hs-varid'>isImmutableTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isSkolemTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isMetaTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isBoxyTyVar</span><span class='hs-layout'>,</span> 
<a name="line-15"></a>  <span class='hs-varid'>isSigTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isExistentialTyVar</span><span class='hs-layout'>,</span>  <span class='hs-varid'>isTyConableTyVar</span><span class='hs-layout'>,</span>
<a name="line-16"></a>  <span class='hs-varid'>metaTvRef</span><span class='hs-layout'>,</span> 
<a name="line-17"></a>  <span class='hs-varid'>isFlexi</span><span class='hs-layout'>,</span> <span class='hs-varid'>isIndirect</span><span class='hs-layout'>,</span> <span class='hs-varid'>isRuntimeUnk</span><span class='hs-layout'>,</span> <span class='hs-varid'>isUnk</span><span class='hs-layout'>,</span>
<a name="line-18"></a>
<a name="line-19"></a>  <span class='hs-comment'>--------------------------------</span>
<a name="line-20"></a>  <span class='hs-comment'>-- Builders</span>
<a name="line-21"></a>  <span class='hs-varid'>mkPhiTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkSigmaTy</span><span class='hs-layout'>,</span> 
<a name="line-22"></a>
<a name="line-23"></a>  <span class='hs-comment'>--------------------------------</span>
<a name="line-24"></a>  <span class='hs-comment'>-- Splitters  </span>
<a name="line-25"></a>  <span class='hs-comment'>-- These are important because they do not look through newtypes</span>
<a name="line-26"></a>  <span class='hs-varid'>tcView</span><span class='hs-layout'>,</span>
<a name="line-27"></a>  <span class='hs-varid'>tcSplitForAllTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitPhiTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitPredFunTy_maybe</span><span class='hs-layout'>,</span>
<a name="line-28"></a>  <span class='hs-varid'>tcSplitFunTy_maybe</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitFunTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcFunArgTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcFunResultTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitFunTysN</span><span class='hs-layout'>,</span>
<a name="line-29"></a>  <span class='hs-varid'>tcSplitTyConApp</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcTyConAppTyCon</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcTyConAppArgs</span><span class='hs-layout'>,</span>
<a name="line-30"></a>  <span class='hs-varid'>tcSplitAppTy_maybe</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitAppTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitAppTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>repSplitAppTy_maybe</span><span class='hs-layout'>,</span>
<a name="line-31"></a>  <span class='hs-varid'>tcInstHeadTyNotSynonym</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcInstHeadTyAppAllTyVars</span><span class='hs-layout'>,</span>
<a name="line-32"></a>  <span class='hs-varid'>tcGetTyVar_maybe</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcGetTyVar</span><span class='hs-layout'>,</span>
<a name="line-33"></a>  <span class='hs-varid'>tcSplitSigmaTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcMultiSplitSigmaTy</span><span class='hs-layout'>,</span> 
<a name="line-34"></a>
<a name="line-35"></a>  <span class='hs-comment'>---------------------------------</span>
<a name="line-36"></a>  <span class='hs-comment'>-- Predicates. </span>
<a name="line-37"></a>  <span class='hs-comment'>-- Again, newtypes are opaque</span>
<a name="line-38"></a>  <span class='hs-varid'>tcEqType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcEqTypes</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcEqPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcCmpType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcCmpTypes</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcCmpPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcEqTypeX</span><span class='hs-layout'>,</span>
<a name="line-39"></a>  <span class='hs-varid'>eqKind</span><span class='hs-layout'>,</span> 
<a name="line-40"></a>  <span class='hs-varid'>isSigmaTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isOverloadedTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isRigidTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isBoxyTy</span><span class='hs-layout'>,</span>
<a name="line-41"></a>  <span class='hs-varid'>isDoubleTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isFloatTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isIntTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isWordTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isStringTy</span><span class='hs-layout'>,</span>
<a name="line-42"></a>  <span class='hs-varid'>isIntegerTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isBoolTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isUnitTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isCharTy</span><span class='hs-layout'>,</span>
<a name="line-43"></a>  <span class='hs-varid'>isTauTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isTauTyCon</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcIsTyVarTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcIsForAllTy</span><span class='hs-layout'>,</span> 
<a name="line-44"></a>  <span class='hs-varid'>isOpenSynTyConApp</span><span class='hs-layout'>,</span>
<a name="line-45"></a>
<a name="line-46"></a>  <span class='hs-comment'>---------------------------------</span>
<a name="line-47"></a>  <span class='hs-comment'>-- Misc type manipulators</span>
<a name="line-48"></a>  <span class='hs-varid'>deNoteType</span><span class='hs-layout'>,</span>
<a name="line-49"></a>  <span class='hs-varid'>tyClsNamesOfType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tyClsNamesOfDFunHead</span><span class='hs-layout'>,</span> 
<a name="line-50"></a>  <span class='hs-varid'>getDFunTyKey</span><span class='hs-layout'>,</span>
<a name="line-51"></a>
<a name="line-52"></a>  <span class='hs-comment'>---------------------------------</span>
<a name="line-53"></a>  <span class='hs-comment'>-- Predicate types  </span>
<a name="line-54"></a>  <span class='hs-varid'>getClassPredTys_maybe</span><span class='hs-layout'>,</span> <span class='hs-varid'>getClassPredTys</span><span class='hs-layout'>,</span> 
<a name="line-55"></a>  <span class='hs-varid'>isClassPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>isTyVarClassPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>isEqPred</span><span class='hs-layout'>,</span> 
<a name="line-56"></a>  <span class='hs-varid'>mkDictTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitPredTy_maybe</span><span class='hs-layout'>,</span> 
<a name="line-57"></a>  <span class='hs-varid'>isPredTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isDictTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isDictLikeTy</span><span class='hs-layout'>,</span>
<a name="line-58"></a>  <span class='hs-varid'>tcSplitDFunTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcSplitDFunHead</span><span class='hs-layout'>,</span> <span class='hs-varid'>predTyUnique</span><span class='hs-layout'>,</span> 
<a name="line-59"></a>  <span class='hs-varid'>mkClassPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>isInheritablePred</span><span class='hs-layout'>,</span> <span class='hs-varid'>isIPPred</span><span class='hs-layout'>,</span> 
<a name="line-60"></a>  <span class='hs-varid'>isRefineableTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isRefineablePred</span><span class='hs-layout'>,</span>
<a name="line-61"></a>
<a name="line-62"></a>  <span class='hs-comment'>---------------------------------</span>
<a name="line-63"></a>  <span class='hs-comment'>-- Foreign import and export</span>
<a name="line-64"></a>  <span class='hs-varid'>isFFIArgumentTy</span><span class='hs-layout'>,</span>     <span class='hs-comment'>-- :: DynFlags -&gt; Safety -&gt; Type -&gt; Bool</span>
<a name="line-65"></a>  <span class='hs-varid'>isFFIImportResultTy</span><span class='hs-layout'>,</span> <span class='hs-comment'>-- :: DynFlags -&gt; Type -&gt; Bool</span>
<a name="line-66"></a>  <span class='hs-varid'>isFFIExportResultTy</span><span class='hs-layout'>,</span> <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-67"></a>  <span class='hs-varid'>isFFIExternalTy</span><span class='hs-layout'>,</span>     <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-68"></a>  <span class='hs-varid'>isFFIDynArgumentTy</span><span class='hs-layout'>,</span>  <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-69"></a>  <span class='hs-varid'>isFFIDynResultTy</span><span class='hs-layout'>,</span>    <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-70"></a>  <span class='hs-varid'>isFFIPrimArgumentTy</span><span class='hs-layout'>,</span> <span class='hs-comment'>-- :: DynFlags -&gt; Type -&gt; Bool</span>
<a name="line-71"></a>  <span class='hs-varid'>isFFIPrimResultTy</span><span class='hs-layout'>,</span>   <span class='hs-comment'>-- :: DynFlags -&gt; Type -&gt; Bool</span>
<a name="line-72"></a>  <span class='hs-varid'>isFFILabelTy</span><span class='hs-layout'>,</span>        <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-73"></a>  <span class='hs-varid'>isFFIDotnetTy</span><span class='hs-layout'>,</span>       <span class='hs-comment'>-- :: DynFlags -&gt; Type -&gt; Bool</span>
<a name="line-74"></a>  <span class='hs-varid'>isFFIDotnetObjTy</span><span class='hs-layout'>,</span>    <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-75"></a>  <span class='hs-varid'>isFFITy</span><span class='hs-layout'>,</span>	       <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-76"></a>  <span class='hs-varid'>isFunPtrTy</span><span class='hs-layout'>,</span>          <span class='hs-comment'>-- :: Type -&gt; Bool</span>
<a name="line-77"></a>  <span class='hs-varid'>tcSplitIOType_maybe</span><span class='hs-layout'>,</span> <span class='hs-comment'>-- :: Type -&gt; Maybe Type  </span>
<a name="line-78"></a>
<a name="line-79"></a>  <span class='hs-comment'>--------------------------------</span>
<a name="line-80"></a>  <span class='hs-comment'>-- Rexported from Type</span>
<a name="line-81"></a>  <span class='hs-conid'>Kind</span><span class='hs-layout'>,</span> 	<span class='hs-comment'>-- Stuff to do with kinds is insensitive to pre/post Tc</span>
<a name="line-82"></a>  <span class='hs-varid'>unliftedTypeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>liftedTypeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>argTypeKind</span><span class='hs-layout'>,</span>
<a name="line-83"></a>  <span class='hs-varid'>openTypeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkArrowKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkArrowKinds</span><span class='hs-layout'>,</span> 
<a name="line-84"></a>  <span class='hs-varid'>isLiftedTypeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>isUnliftedTypeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>isSubOpenTypeKind</span><span class='hs-layout'>,</span> 
<a name="line-85"></a>  <span class='hs-varid'>isSubArgTypeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>isSubKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>splitKindFunTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>defaultKind</span><span class='hs-layout'>,</span>
<a name="line-86"></a>  <span class='hs-varid'>kindVarRef</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkKindVar</span><span class='hs-layout'>,</span>  
<a name="line-87"></a>
<a name="line-88"></a>  <span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-conid'>PredType</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-conid'>ThetaType</span><span class='hs-layout'>,</span> 
<a name="line-89"></a>  <span class='hs-varid'>mkForAllTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkForAllTys</span><span class='hs-layout'>,</span> 
<a name="line-90"></a>  <span class='hs-varid'>mkFunTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkFunTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>zipFunTys</span><span class='hs-layout'>,</span> 
<a name="line-91"></a>  <span class='hs-varid'>mkTyConApp</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkAppTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkAppTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>applyTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>applyTys</span><span class='hs-layout'>,</span>
<a name="line-92"></a>  <span class='hs-varid'>mkTyVarTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkTyVarTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkTyConTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkPredTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkPredTys</span><span class='hs-layout'>,</span> 
<a name="line-93"></a>
<a name="line-94"></a>  <span class='hs-comment'>-- Type substitutions</span>
<a name="line-95"></a>  <span class='hs-conid'>TvSubst</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> 	<span class='hs-comment'>-- Representation visible to a few friends</span>
<a name="line-96"></a>  <span class='hs-conid'>TvSubstEnv</span><span class='hs-layout'>,</span> <span class='hs-varid'>emptyTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>substEqSpec</span><span class='hs-layout'>,</span>
<a name="line-97"></a>  <span class='hs-varid'>mkOpenTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>zipOpenTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>zipTopTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkTopTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>notElemTvSubst</span><span class='hs-layout'>,</span>
<a name="line-98"></a>  <span class='hs-varid'>getTvSubstEnv</span><span class='hs-layout'>,</span> <span class='hs-varid'>setTvSubstEnv</span><span class='hs-layout'>,</span> <span class='hs-varid'>getTvInScope</span><span class='hs-layout'>,</span> <span class='hs-varid'>extendTvInScope</span><span class='hs-layout'>,</span> <span class='hs-varid'>lookupTyVar</span><span class='hs-layout'>,</span>
<a name="line-99"></a>  <span class='hs-varid'>extendTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>extendTvSubstList</span><span class='hs-layout'>,</span> <span class='hs-varid'>isInScope</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkTvSubst</span><span class='hs-layout'>,</span> <span class='hs-varid'>zipTyEnv</span><span class='hs-layout'>,</span>
<a name="line-100"></a>  <span class='hs-varid'>substTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTys</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTyWith</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTheta</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTyVars</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTyVarBndr</span><span class='hs-layout'>,</span>
<a name="line-101"></a>
<a name="line-102"></a>  <span class='hs-varid'>isUnLiftedType</span><span class='hs-layout'>,</span>	<span class='hs-comment'>-- Source types are always lifted</span>
<a name="line-103"></a>  <span class='hs-varid'>isUnboxedTupleType</span><span class='hs-layout'>,</span>	<span class='hs-comment'>-- Ditto</span>
<a name="line-104"></a>  <span class='hs-varid'>isPrimitiveType</span><span class='hs-layout'>,</span> 
<a name="line-105"></a>
<a name="line-106"></a>  <span class='hs-varid'>tidyTopType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyTypes</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyFreeTyVars</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyOpenType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyOpenTypes</span><span class='hs-layout'>,</span>
<a name="line-107"></a>  <span class='hs-varid'>tidyTyVarBndr</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyOpenTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyOpenTyVars</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidySkolemTyVar</span><span class='hs-layout'>,</span>
<a name="line-108"></a>  <span class='hs-varid'>typeKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>tidyKind</span><span class='hs-layout'>,</span>
<a name="line-109"></a>
<a name="line-110"></a>  <span class='hs-varid'>tyVarsOfType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tyVarsOfTypes</span><span class='hs-layout'>,</span> <span class='hs-varid'>tyVarsOfPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>tyVarsOfTheta</span><span class='hs-layout'>,</span>
<a name="line-111"></a>  <span class='hs-varid'>tcTyVarsOfType</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcTyVarsOfTypes</span><span class='hs-layout'>,</span> <span class='hs-varid'>tcTyVarsOfPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>exactTyVarsOfType</span><span class='hs-layout'>,</span>
<a name="line-112"></a>  <span class='hs-varid'>exactTyVarsOfTypes</span><span class='hs-layout'>,</span> 
<a name="line-113"></a>
<a name="line-114"></a>  <span class='hs-varid'>pprKind</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprParendKind</span><span class='hs-layout'>,</span>
<a name="line-115"></a>  <span class='hs-varid'>pprType</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprParendType</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprTypeApp</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprTyThingCategory</span><span class='hs-layout'>,</span>
<a name="line-116"></a>  <span class='hs-varid'>pprPred</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprTheta</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprThetaArrow</span><span class='hs-layout'>,</span> <span class='hs-varid'>pprClassPred</span>
<a name="line-117"></a>
<a name="line-118"></a>  <span class='hs-layout'>)</span> <span class='hs-keyword'>where</span>
<a name="line-119"></a>
<a name="line-120"></a><span class='hs-cpp'>#include "HsVersions.h"</span>
<a name="line-121"></a>
<a name="line-122"></a><span class='hs-comment'>-- friends:</span>
<a name="line-123"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>TypeRep</span>
<a name="line-124"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>DataCon</span>
<a name="line-125"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Class</span>
<a name="line-126"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Var</span>
<a name="line-127"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>ForeignCall</span>
<a name="line-128"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>VarSet</span>
<a name="line-129"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Type</span>
<a name="line-130"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Coercion</span>
<a name="line-131"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>TyCon</span>
<a name="line-132"></a>
<a name="line-133"></a><span class='hs-comment'>-- others:</span>
<a name="line-134"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>DynFlags</span>
<a name="line-135"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Name</span>
<a name="line-136"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>NameSet</span>
<a name="line-137"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>VarEnv</span>
<a name="line-138"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>PrelNames</span>
<a name="line-139"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>TysWiredIn</span>
<a name="line-140"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>BasicTypes</span>
<a name="line-141"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Util</span>
<a name="line-142"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Maybes</span>
<a name="line-143"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>ListSetOps</span>
<a name="line-144"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Outputable</span>
<a name="line-145"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>FastString</span>
<a name="line-146"></a>
<a name="line-147"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>IORef</span>
</pre>\end{code}

%************************************************************************
%*									*
\subsection{Types}
%*									*
%************************************************************************

The type checker divides the generic Type world into the 
following more structured beasts:

sigma ::= forall tyvars. phi
	-- A sigma type is a qualified type
	--
	-- Note that even if 'tyvars' is empty, theta
	-- may not be: e.g.   (?x::Int) => Int

	-- Note that 'sigma' is in prenex form:
	-- all the foralls are at the front.
	-- A 'phi' type has no foralls to the right of
	-- an arrow

phi :: theta => rho

rho ::= sigma -> rho
     |  tau

-- A 'tau' type has no quantification anywhere
-- Note that the args of a type constructor must be taus
tau ::= tyvar
     |  tycon tau_1 .. tau_n
     |  tau_1 tau_2
     |  tau_1 -> tau_2

-- In all cases, a (saturated) type synonym application is legal,
-- provided it expands to the required form.

\begin{code}
<pre><a name="line-1"></a><a name="TcTyVar"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcTyVar</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TyVar</span>  	<span class='hs-comment'>-- Used only during type inference</span>
<a name="line-2"></a><a name="TcType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcType</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Type</span> 	<span class='hs-comment'>-- A TcType can have mutable type variables</span>
<a name="line-3"></a>	<span class='hs-comment'>-- Invariant on ForAllTy in TcTypes:</span>
<a name="line-4"></a>	<span class='hs-comment'>-- 	forall a. T</span>
<a name="line-5"></a>	<span class='hs-comment'>-- a cannot occur inside a MutTyVar in T; that is,</span>
<a name="line-6"></a>	<span class='hs-comment'>-- T is "flattened" before quantifying over a</span>
<a name="line-7"></a>
<a name="line-8"></a><a name="TcPredType"></a><span class='hs-comment'>-- These types do not have boxy type variables in them</span>
<a name="line-9"></a><a name="TcPredType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcPredType</span>     <span class='hs-keyglyph'>=</span> <span class='hs-conid'>PredType</span>
<a name="line-10"></a><a name="TcThetaType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcThetaType</span>    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ThetaType</span>
<a name="line-11"></a><a name="TcSigmaType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcSigmaType</span>    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcType</span>
<a name="line-12"></a><a name="TcRhoType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcRhoType</span>      <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcType</span>
<a name="line-13"></a><a name="TcTauType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcTauType</span>      <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcType</span>
<a name="line-14"></a><a name="TcKind"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcKind</span>         <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Kind</span>
<a name="line-15"></a><a name="TcTyVarSet"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>TcTyVarSet</span>     <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TyVarSet</span>
<a name="line-16"></a>
<a name="line-17"></a><a name="BoxyTyVar"></a><span class='hs-comment'>-- These types may have boxy type variables in them</span>
<a name="line-18"></a><a name="BoxyTyVar"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>BoxyTyVar</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcTyVar</span>
<a name="line-19"></a><a name="BoxyRhoType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>BoxyRhoType</span>    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcType</span>	
<a name="line-20"></a><a name="BoxyThetaType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>BoxyThetaType</span>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcThetaType</span>	
<a name="line-21"></a><a name="BoxySigmaType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>BoxySigmaType</span>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcType</span>		
<a name="line-22"></a><a name="BoxyType"></a><span class='hs-keyword'>type</span> <span class='hs-conid'>BoxyType</span>       <span class='hs-keyglyph'>=</span> <span class='hs-conid'>TcType</span>		
</pre>\end{code}


%************************************************************************
%*									*
\subsection{TyVarDetails}
%*									*
%************************************************************************

TyVarDetails gives extra info about type variables, used during type
checking.  It's attached to mutable type variables only.
It's knot-tied back to Var.lhs.  There is no reason in principle
why Var.lhs shouldn't actually have the definition, but it "belongs" here.


Note [Signature skolems]
~~~~~~~~~~~~~~~~~~~~~~~~
Consider this

  x :: [a]
  y :: b
  (x,y,z) = ([y,z], z, head x)

Here, x and y have type sigs, which go into the environment.  We used to
instantiate their types with skolem constants, and push those types into
the RHS, so we'd typecheck the RHS with type
	( [a*], b*, c )
where a*, b* are skolem constants, and c is an ordinary meta type varible.

The trouble is that the occurrences of z in the RHS force a* and b* to 
be the *same*, so we can't make them into skolem constants that don't unify
with each other.  Alas.

One solution would be insist that in the above defn the programmer uses
the same type variable in both type signatures.  But that takes explanation.

The alternative (currently implemented) is to have a special kind of skolem
constant, SigTv, which can unify with other SigTvs.  These are *not* treated
as righd for the purposes of GADTs.  And they are used *only* for pattern 
bindings and mutually recursive function bindings.  See the function
TcBinds.tcInstSig, and its use_skols parameter.


\begin{code}
<pre><a name="line-1"></a><a name="TcTyVarDetails"></a><span class='hs-comment'>-- A TyVarDetails is inside a TyVar</span>
<a name="line-2"></a><a name="TcTyVarDetails"></a><span class='hs-keyword'>data</span> <span class='hs-conid'>TcTyVarDetails</span>
<a name="line-3"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>SkolemTv</span> <span class='hs-conid'>SkolemInfo</span>			<span class='hs-comment'>-- A skolem constant</span>
<a name="line-4"></a>
<a name="line-5"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>MetaTv</span> <span class='hs-conid'>BoxInfo</span> <span class='hs-layout'>(</span><span class='hs-conid'>IORef</span> <span class='hs-conid'>MetaDetails</span><span class='hs-layout'>)</span>
<a name="line-6"></a>
<a name="line-7"></a><a name="BoxInfo"></a><span class='hs-keyword'>data</span> <span class='hs-conid'>BoxInfo</span> 
<a name="line-8"></a>   <span class='hs-keyglyph'>=</span> <span class='hs-conid'>BoxTv</span>	<span class='hs-comment'>-- The contents is a (non-boxy) sigma-type</span>
<a name="line-9"></a>		<span class='hs-comment'>-- That is, this MetaTv is a "box"</span>
<a name="line-10"></a>
<a name="line-11"></a>   <span class='hs-keyglyph'>|</span> <span class='hs-conid'>TauTv</span>	<span class='hs-comment'>-- The contents is a (non-boxy) tau-type</span>
<a name="line-12"></a>		<span class='hs-comment'>-- That is, this MetaTv is an ordinary unification variable</span>
<a name="line-13"></a>
<a name="line-14"></a>   <span class='hs-keyglyph'>|</span> <span class='hs-conid'>SigTv</span> <span class='hs-conid'>SkolemInfo</span>	<span class='hs-comment'>-- A variant of TauTv, except that it should not be</span>
<a name="line-15"></a>			<span class='hs-comment'>-- unified with a type, only with a type variable</span>
<a name="line-16"></a>			<span class='hs-comment'>-- SigTvs are only distinguished to improve error messages</span>
<a name="line-17"></a>			<span class='hs-comment'>--      see Note [Signature skolems]        </span>
<a name="line-18"></a>			<span class='hs-comment'>--      The MetaDetails, if filled in, will </span>
<a name="line-19"></a>			<span class='hs-comment'>--      always be another SigTv or a SkolemTv</span>
<a name="line-20"></a>
<a name="line-21"></a><span class='hs-comment'>-- INVARIANTS:</span>
<a name="line-22"></a><span class='hs-comment'>--  	A TauTv is always filled in with a tau-type, which</span>
<a name="line-23"></a><span class='hs-comment'>--	never contains any BoxTvs, nor any ForAlls </span>
<a name="line-24"></a><span class='hs-comment'>--</span>
<a name="line-25"></a><span class='hs-comment'>--	However, a BoxTv can contain a type that contains further BoxTvs</span>
<a name="line-26"></a><span class='hs-comment'>--	Notably, when typechecking an explicit list, say [e1,e2], with</span>
<a name="line-27"></a><span class='hs-comment'>--	expected type being a box b1, we fill in b1 with (List b2), where</span>
<a name="line-28"></a><span class='hs-comment'>--	b2 is another (currently empty) box.</span>
<a name="line-29"></a>
<a name="line-30"></a><a name="MetaDetails"></a><span class='hs-keyword'>data</span> <span class='hs-conid'>MetaDetails</span>
<a name="line-31"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Flexi</span>	        <span class='hs-comment'>-- Flexi type variables unify to become </span>
<a name="line-32"></a>                   	<span class='hs-comment'>-- Indirects.  </span>
<a name="line-33"></a>
<a name="line-34"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Indirect</span> <span class='hs-conid'>TcType</span>  	<span class='hs-comment'>-- INVARIANT:</span>
<a name="line-35"></a>		     	<span class='hs-comment'>--   For a BoxTv, this type must be non-boxy</span>
<a name="line-36"></a>                     	<span class='hs-comment'>--   For a TauTv, this type must be a tau-type</span>
<a name="line-37"></a>
<a name="line-38"></a><a name="SkolemInfo"></a><span class='hs-comment'>-- Generally speaking, SkolemInfo should not contain location info</span>
<a name="line-39"></a><a name="SkolemInfo"></a><span class='hs-comment'>-- that is contained in the Name of the tyvar with this SkolemInfo</span>
<a name="line-40"></a><a name="SkolemInfo"></a><span class='hs-keyword'>data</span> <span class='hs-conid'>SkolemInfo</span>
<a name="line-41"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>SigSkol</span> <span class='hs-conid'>UserTypeCtxt</span>	<span class='hs-comment'>-- A skolem that is created by instantiating</span>
<a name="line-42"></a>				<span class='hs-comment'>-- a programmer-supplied type signature</span>
<a name="line-43"></a>				<span class='hs-comment'>-- Location of the binding site is on the TyVar</span>
<a name="line-44"></a>
<a name="line-45"></a>	<span class='hs-comment'>-- The rest are for non-scoped skolems</span>
<a name="line-46"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ClsSkol</span> <span class='hs-conid'>Class</span>	<span class='hs-comment'>-- Bound at a class decl</span>
<a name="line-47"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>InstSkol</span> 		<span class='hs-comment'>-- Bound at an instance decl</span>
<a name="line-48"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>FamInstSkol</span> 	<span class='hs-comment'>-- Bound at a family instance decl</span>
<a name="line-49"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>PatSkol</span> <span class='hs-conid'>DataCon</span>	<span class='hs-comment'>-- An existential type variable bound by a pattern for</span>
<a name="line-50"></a>	    		<span class='hs-comment'>-- a data constructor with an existential type. E.g.</span>
<a name="line-51"></a>			<span class='hs-comment'>--	data T = forall a. Eq a =&gt; MkT a</span>
<a name="line-52"></a>			<span class='hs-comment'>-- 	f (MkT x) = ...</span>
<a name="line-53"></a>			<span class='hs-comment'>-- The pattern MkT x will allocate an existential type</span>
<a name="line-54"></a>			<span class='hs-comment'>-- variable for 'a'.  </span>
<a name="line-55"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ArrowSkol</span> 		<span class='hs-comment'>-- An arrow form (see TcArrows)</span>
<a name="line-56"></a>
<a name="line-57"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>RuleSkol</span> <span class='hs-conid'>RuleName</span>	<span class='hs-comment'>-- The LHS of a RULE</span>
<a name="line-58"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>GenSkol</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>TcTyVar</span><span class='hs-keyglyph'>]</span>	<span class='hs-comment'>-- Bound when doing a subsumption check for </span>
<a name="line-59"></a>	    <span class='hs-conid'>TcType</span>	<span class='hs-comment'>-- 	(forall tvs. ty)</span>
<a name="line-60"></a>
<a name="line-61"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>RuntimeUnkSkol</span>      <span class='hs-comment'>-- a type variable used to represent an unknown</span>
<a name="line-62"></a>                        <span class='hs-comment'>-- runtime type (used in the GHCi debugger)</span>
<a name="line-63"></a>
<a name="line-64"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>UnkSkol</span>		<span class='hs-comment'>-- Unhelpful info (until I improve it)</span>
<a name="line-65"></a>
<a name="line-66"></a><a name="UserTypeCtxt"></a><span class='hs-comment'>-------------------------------------</span>
<a name="line-67"></a><a name="UserTypeCtxt"></a><span class='hs-comment'>-- UserTypeCtxt describes the places where a </span>
<a name="line-68"></a><a name="UserTypeCtxt"></a><span class='hs-comment'>-- programmer-written type signature can occur</span>
<a name="line-69"></a><a name="UserTypeCtxt"></a><span class='hs-comment'>-- Like SkolemInfo, no location info</span>
<a name="line-70"></a><a name="UserTypeCtxt"></a><span class='hs-keyword'>data</span> <span class='hs-conid'>UserTypeCtxt</span> 
<a name="line-71"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>FunSigCtxt</span> <span class='hs-conid'>Name</span>	<span class='hs-comment'>-- Function type signature</span>
<a name="line-72"></a>			<span class='hs-comment'>-- Also used for types in SPECIALISE pragmas</span>
<a name="line-73"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ExprSigCtxt</span>		<span class='hs-comment'>-- Expression type signature</span>
<a name="line-74"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ConArgCtxt</span> <span class='hs-conid'>Name</span>	<span class='hs-comment'>-- Data constructor argument</span>
<a name="line-75"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>TySynCtxt</span> <span class='hs-conid'>Name</span>	<span class='hs-comment'>-- RHS of a type synonym decl</span>
<a name="line-76"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>GenPatCtxt</span>		<span class='hs-comment'>-- Pattern in generic decl</span>
<a name="line-77"></a>			<span class='hs-comment'>-- 	f{| a+b |} (Inl x) = ...</span>
<a name="line-78"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>LamPatSigCtxt</span>		<span class='hs-comment'>-- Type sig in lambda pattern</span>
<a name="line-79"></a>			<span class='hs-comment'>-- 	f (x::t) = ...</span>
<a name="line-80"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>BindPatSigCtxt</span>	<span class='hs-comment'>-- Type sig in pattern binding pattern</span>
<a name="line-81"></a>			<span class='hs-comment'>--	(x::t, y) = e</span>
<a name="line-82"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ResSigCtxt</span>		<span class='hs-comment'>-- Result type sig</span>
<a name="line-83"></a>			<span class='hs-comment'>-- 	f x :: t = ....</span>
<a name="line-84"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ForSigCtxt</span> <span class='hs-conid'>Name</span>	<span class='hs-comment'>-- Foreign inport or export signature</span>
<a name="line-85"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>DefaultDeclCtxt</span>	<span class='hs-comment'>-- Types in a default declaration</span>
<a name="line-86"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>SpecInstCtxt</span>	<span class='hs-comment'>-- SPECIALISE instance pragma</span>
<a name="line-87"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>ThBrackCtxt</span>		<span class='hs-comment'>-- Template Haskell type brackets [t| ... |]</span>
<a name="line-88"></a>
<a name="line-89"></a><span class='hs-comment'>-- Notes re TySynCtxt</span>
<a name="line-90"></a><span class='hs-comment'>-- We allow type synonyms that aren't types; e.g.  type List = []</span>
<a name="line-91"></a><span class='hs-comment'>--</span>
<a name="line-92"></a><span class='hs-comment'>-- If the RHS mentions tyvars that aren't in scope, we'll </span>
<a name="line-93"></a><span class='hs-comment'>-- quantify over them:</span>
<a name="line-94"></a><span class='hs-comment'>--	e.g. 	type T = a-&gt;a</span>
<a name="line-95"></a><span class='hs-comment'>-- will become	type T = forall a. a-&gt;a</span>
<a name="line-96"></a><span class='hs-comment'>--</span>
<a name="line-97"></a><span class='hs-comment'>-- With gla-exts that's right, but for H98 we should complain. </span>
<a name="line-98"></a>
<a name="line-99"></a><span class='hs-comment'>---------------------------------</span>
<a name="line-100"></a><span class='hs-comment'>-- Kind variables:</span>
<a name="line-101"></a>
<a name="line-102"></a><a name="mkKindName"></a><span class='hs-definition'>mkKindName</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Unique</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Name</span>
<a name="line-103"></a><span class='hs-definition'>mkKindName</span> <span class='hs-varid'>unique</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>mkSystemName</span> <span class='hs-varid'>unique</span> <span class='hs-varid'>kind_var_occ</span>
<a name="line-104"></a>
<a name="line-105"></a><a name="kindVarRef"></a><span class='hs-definition'>kindVarRef</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>KindVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>IORef</span> <span class='hs-conid'>MetaDetails</span>
<a name="line-106"></a><span class='hs-definition'>kindVarRef</span> <span class='hs-varid'>tc</span> <span class='hs-keyglyph'>=</span> 
<a name="line-107"></a>  <span class='hs-conid'>ASSERT</span> <span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tc</span> <span class='hs-layout'>)</span>
<a name="line-108"></a>  <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tc</span> <span class='hs-keyword'>of</span>
<a name="line-109"></a>    <span class='hs-conid'>MetaTv</span> <span class='hs-conid'>TauTv</span> <span class='hs-varid'>ref</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>ref</span>
<a name="line-110"></a>    <span class='hs-keyword'>_</span>                <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"kindVarRef"</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>tc</span><span class='hs-layout'>)</span>
<a name="line-111"></a>
<a name="line-112"></a><a name="mkKindVar"></a><span class='hs-definition'>mkKindVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Unique</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>IORef</span> <span class='hs-conid'>MetaDetails</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>KindVar</span>
<a name="line-113"></a><span class='hs-definition'>mkKindVar</span> <span class='hs-varid'>u</span> <span class='hs-varid'>r</span> 
<a name="line-114"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>mkTcTyVar</span> <span class='hs-layout'>(</span><span class='hs-varid'>mkKindName</span> <span class='hs-varid'>u</span><span class='hs-layout'>)</span>
<a name="line-115"></a>              <span class='hs-varid'>tySuperKind</span>  <span class='hs-comment'>-- not sure this is right,</span>
<a name="line-116"></a>                            <span class='hs-comment'>-- do we need kind vars for</span>
<a name="line-117"></a>                            <span class='hs-comment'>-- coercions?</span>
<a name="line-118"></a>              <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-conid'>TauTv</span> <span class='hs-varid'>r</span><span class='hs-layout'>)</span>
<a name="line-119"></a>
<a name="line-120"></a><a name="kind_var_occ"></a><span class='hs-definition'>kind_var_occ</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>OccName</span>	<span class='hs-comment'>-- Just one for all KindVars</span>
<a name="line-121"></a>			<span class='hs-comment'>-- They may be jiggled by tidying</span>
<a name="line-122"></a><span class='hs-definition'>kind_var_occ</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>mkOccName</span> <span class='hs-varid'>tvName</span> <span class='hs-str'>"k"</span>
</pre>\end{code}

%************************************************************************
%*									*
		Pretty-printing
%*									*
%************************************************************************

\begin{code}
<pre><a name="line-1"></a><a name="pprTcTyVarDetails"></a><span class='hs-definition'>pprTcTyVarDetails</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcTyVarDetails</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>SDoc</span>
<a name="line-2"></a><span class='hs-comment'>-- For debugging</span>
<a name="line-3"></a><span class='hs-definition'>pprTcTyVarDetails</span> <span class='hs-layout'>(</span><span class='hs-conid'>SkolemTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>         <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"sk"</span><span class='hs-layout'>)</span>
<a name="line-4"></a><span class='hs-definition'>pprTcTyVarDetails</span> <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-conid'>BoxTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"box"</span><span class='hs-layout'>)</span>
<a name="line-5"></a><span class='hs-definition'>pprTcTyVarDetails</span> <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-conid'>TauTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"tau"</span><span class='hs-layout'>)</span>
<a name="line-6"></a><span class='hs-definition'>pprTcTyVarDetails</span> <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"sig"</span><span class='hs-layout'>)</span>
<a name="line-7"></a>
<a name="line-8"></a><a name="pprUserTypeCtxt"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>UserTypeCtxt</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>SDoc</span>
<a name="line-9"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunSigCtxt</span> <span class='hs-varid'>n</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the type signature for"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>n</span><span class='hs-layout'>)</span>
<a name="line-10"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>ExprSigCtxt</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"an expression type signature"</span><span class='hs-layout'>)</span>
<a name="line-11"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-layout'>(</span><span class='hs-conid'>ConArgCtxt</span> <span class='hs-varid'>c</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the type of the constructor"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>c</span><span class='hs-layout'>)</span>
<a name="line-12"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-layout'>(</span><span class='hs-conid'>TySynCtxt</span> <span class='hs-varid'>c</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the RHS of the type synonym"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>c</span><span class='hs-layout'>)</span>
<a name="line-13"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>GenPatCtxt</span>      <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the type pattern of a generic definition"</span><span class='hs-layout'>)</span>
<a name="line-14"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>ThBrackCtxt</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"a Template Haskell quotation [t|...|]"</span><span class='hs-layout'>)</span>
<a name="line-15"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>LamPatSigCtxt</span>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"a pattern type signature"</span><span class='hs-layout'>)</span>
<a name="line-16"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>BindPatSigCtxt</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"a pattern type signature"</span><span class='hs-layout'>)</span>
<a name="line-17"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>ResSigCtxt</span>      <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"a result type signature"</span><span class='hs-layout'>)</span>
<a name="line-18"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForSigCtxt</span> <span class='hs-varid'>n</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the foreign declaration for"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>n</span><span class='hs-layout'>)</span>
<a name="line-19"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>DefaultDeclCtxt</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"a type in a `default' declaration"</span><span class='hs-layout'>)</span>
<a name="line-20"></a><span class='hs-definition'>pprUserTypeCtxt</span> <span class='hs-conid'>SpecInstCtxt</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"a SPECIALISE instance pragma"</span><span class='hs-layout'>)</span>
<a name="line-21"></a>
<a name="line-22"></a>
<a name="line-23"></a><a name="tidySkolemTyVar"></a><span class='hs-comment'>--------------------------------</span>
<a name="line-24"></a><span class='hs-definition'>tidySkolemTyVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TidyEnv</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TcTyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>TidyEnv</span><span class='hs-layout'>,</span> <span class='hs-conid'>TcTyVar</span><span class='hs-layout'>)</span>
<a name="line-25"></a><span class='hs-comment'>-- Tidy the type inside a GenSkol, preparatory to printing it</span>
<a name="line-26"></a><span class='hs-definition'>tidySkolemTyVar</span> <span class='hs-varid'>env</span> <span class='hs-varid'>tv</span>
<a name="line-27"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-layout'>(</span><span class='hs-varid'>isSkolemTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-varop'>||</span> <span class='hs-varid'>isSigTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span> <span class='hs-layout'>)</span>
<a name="line-28"></a>    <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-varid'>mkTcTyVar</span> <span class='hs-layout'>(</span><span class='hs-varid'>tyVarName</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span> <span class='hs-layout'>(</span><span class='hs-varid'>tyVarKind</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span> <span class='hs-varid'>info1</span><span class='hs-layout'>)</span>
<a name="line-29"></a>  <span class='hs-keyword'>where</span>
<a name="line-30"></a>    <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-varid'>info1</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-31"></a>			<span class='hs-conid'>SkolemTv</span> <span class='hs-varid'>info</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-conid'>SkolemTv</span> <span class='hs-varid'>info'</span><span class='hs-layout'>)</span>
<a name="line-32"></a>				<span class='hs-keyword'>where</span>
<a name="line-33"></a>				  <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-varid'>info'</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tidy_skol_info</span> <span class='hs-varid'>env</span> <span class='hs-varid'>info</span>
<a name="line-34"></a>			<span class='hs-conid'>MetaTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigTv</span> <span class='hs-varid'>info</span><span class='hs-layout'>)</span> <span class='hs-varid'>box</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-conid'>MetaTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigTv</span> <span class='hs-varid'>info'</span><span class='hs-layout'>)</span> <span class='hs-varid'>box</span><span class='hs-layout'>)</span>
<a name="line-35"></a>				<span class='hs-keyword'>where</span>
<a name="line-36"></a>				  <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-varid'>info'</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tidy_skol_info</span> <span class='hs-varid'>env</span> <span class='hs-varid'>info</span>
<a name="line-37"></a>			<span class='hs-varid'>info</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>env</span><span class='hs-layout'>,</span> <span class='hs-varid'>info</span><span class='hs-layout'>)</span>
<a name="line-38"></a>
<a name="line-39"></a>    <span class='hs-varid'>tidy_skol_info</span> <span class='hs-varid'>env</span> <span class='hs-layout'>(</span><span class='hs-conid'>GenSkol</span> <span class='hs-varid'>tvs</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>env2</span><span class='hs-layout'>,</span> <span class='hs-conid'>GenSkol</span> <span class='hs-varid'>tvs1</span> <span class='hs-varid'>ty1</span><span class='hs-layout'>)</span>
<a name="line-40"></a>			    <span class='hs-keyword'>where</span>
<a name="line-41"></a>			      <span class='hs-layout'>(</span><span class='hs-varid'>env1</span><span class='hs-layout'>,</span> <span class='hs-varid'>tvs1</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tidyOpenTyVars</span> <span class='hs-varid'>env</span> <span class='hs-varid'>tvs</span>
<a name="line-42"></a>			      <span class='hs-layout'>(</span><span class='hs-varid'>env2</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty1</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tidyOpenType</span> <span class='hs-varid'>env1</span> <span class='hs-varid'>ty</span>
<a name="line-43"></a>    <span class='hs-varid'>tidy_skol_info</span> <span class='hs-varid'>env</span> <span class='hs-varid'>info</span> <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>env</span><span class='hs-layout'>,</span> <span class='hs-varid'>info</span><span class='hs-layout'>)</span>
<a name="line-44"></a>		     
<a name="line-45"></a><a name="pprSkolTvBinding"></a><span class='hs-definition'>pprSkolTvBinding</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcTyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>SDoc</span>
<a name="line-46"></a><span class='hs-comment'>-- Print info about the binding of a skolem tyvar, </span>
<a name="line-47"></a><span class='hs-comment'>-- or nothing if we don't have anything useful to say</span>
<a name="line-48"></a><span class='hs-definition'>pprSkolTvBinding</span> <span class='hs-varid'>tv</span>
<a name="line-49"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span> <span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-50"></a>    <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>ppr_details</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>
<a name="line-51"></a>  <span class='hs-keyword'>where</span>
<a name="line-52"></a>    <span class='hs-varid'>ppr_details</span> <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-conid'>TauTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>   	<span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"is a meta type variable"</span><span class='hs-layout'>)</span>
<a name="line-53"></a>    <span class='hs-varid'>ppr_details</span> <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-conid'>BoxTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>   	<span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"is a boxy type variable"</span><span class='hs-layout'>)</span>
<a name="line-54"></a>    <span class='hs-varid'>ppr_details</span> <span class='hs-layout'>(</span><span class='hs-conid'>MetaTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigTv</span> <span class='hs-varid'>info</span><span class='hs-layout'>)</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ppr_skol</span> <span class='hs-varid'>info</span>
<a name="line-55"></a>    <span class='hs-varid'>ppr_details</span> <span class='hs-layout'>(</span><span class='hs-conid'>SkolemTv</span> <span class='hs-varid'>info</span><span class='hs-layout'>)</span>		<span class='hs-keyglyph'>=</span> <span class='hs-varid'>ppr_skol</span> <span class='hs-varid'>info</span>
<a name="line-56"></a>
<a name="line-57"></a>    <span class='hs-varid'>ppr_skol</span> <span class='hs-conid'>UnkSkol</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"is an unknown type variable"</span><span class='hs-layout'>)</span>	<span class='hs-comment'>-- Unhelpful</span>
<a name="line-58"></a>    <span class='hs-varid'>ppr_skol</span> <span class='hs-conid'>RuntimeUnkSkol</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"is an unknown runtime type"</span><span class='hs-layout'>)</span>
<a name="line-59"></a>    <span class='hs-varid'>ppr_skol</span> <span class='hs-varid'>info</span>           <span class='hs-keyglyph'>=</span> <span class='hs-varid'>sep</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"is a rigid type variable bound by"</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span>
<a name="line-60"></a>				   <span class='hs-varid'>sep</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>pprSkolInfo</span> <span class='hs-varid'>info</span><span class='hs-layout'>,</span> 
<a name="line-61"></a>					 <span class='hs-varid'>nest</span> <span class='hs-num'>2</span> <span class='hs-layout'>(</span><span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"at"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>ppr</span> <span class='hs-layout'>(</span><span class='hs-varid'>getSrcLoc</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span><span class='hs-keyglyph'>]</span><span class='hs-keyglyph'>]</span>
<a name="line-62"></a> 
<a name="line-63"></a><a name="pprSkolInfo"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>SkolemInfo</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>SDoc</span>
<a name="line-64"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigSkol</span> <span class='hs-varid'>ctxt</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>pprUserTypeCtxt</span> <span class='hs-varid'>ctxt</span>
<a name="line-65"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClsSkol</span> <span class='hs-varid'>cls</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the class declaration for"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>cls</span><span class='hs-layout'>)</span>
<a name="line-66"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-conid'>InstSkol</span>         <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the instance declaration"</span><span class='hs-layout'>)</span>
<a name="line-67"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-conid'>FamInstSkol</span>      <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the family instance declaration"</span><span class='hs-layout'>)</span>
<a name="line-68"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-layout'>(</span><span class='hs-conid'>RuleSkol</span> <span class='hs-varid'>name</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the RULE"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>doubleQuotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ftext</span> <span class='hs-varid'>name</span><span class='hs-layout'>)</span>
<a name="line-69"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-conid'>ArrowSkol</span>        <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the arrow form"</span><span class='hs-layout'>)</span>
<a name="line-70"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-layout'>(</span><span class='hs-conid'>PatSkol</span> <span class='hs-varid'>dc</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>sep</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the constructor"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>dc</span><span class='hs-layout'>)</span><span class='hs-keyglyph'>]</span>
<a name="line-71"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-layout'>(</span><span class='hs-conid'>GenSkol</span> <span class='hs-varid'>tvs</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>sep</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"the polymorphic type"</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> 
<a name="line-72"></a>				    <span class='hs-varid'>nest</span> <span class='hs-num'>2</span> <span class='hs-layout'>(</span><span class='hs-varid'>quotes</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-layout'>(</span><span class='hs-varid'>mkForAllTys</span> <span class='hs-varid'>tvs</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span><span class='hs-keyglyph'>]</span>
<a name="line-73"></a>
<a name="line-74"></a><span class='hs-comment'>-- UnkSkol</span>
<a name="line-75"></a><span class='hs-comment'>-- For type variables the others are dealt with by pprSkolTvBinding.  </span>
<a name="line-76"></a><span class='hs-comment'>-- For Insts, these cases should not happen</span>
<a name="line-77"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-conid'>UnkSkol</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>panic</span> <span class='hs-str'>"UnkSkol"</span>
<a name="line-78"></a><span class='hs-definition'>pprSkolInfo</span> <span class='hs-conid'>RuntimeUnkSkol</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>panic</span> <span class='hs-str'>"RuntimeUnkSkol"</span>
<a name="line-79"></a>
<a name="line-80"></a><span class='hs-keyword'>instance</span> <span class='hs-conid'>Outputable</span> <span class='hs-conid'>MetaDetails</span> <span class='hs-keyword'>where</span>
<a name="line-81"></a>  <span class='hs-varid'>ppr</span> <span class='hs-conid'>Flexi</span>         <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"Flexi"</span><span class='hs-layout'>)</span>
<a name="line-82"></a>  <span class='hs-varid'>ppr</span> <span class='hs-layout'>(</span><span class='hs-conid'>Indirect</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ptext</span> <span class='hs-layout'>(</span><span class='hs-varid'>sLit</span> <span class='hs-str'>"Indirect"</span><span class='hs-layout'>)</span> <span class='hs-varop'>&lt;+&gt;</span> <span class='hs-varid'>ppr</span> <span class='hs-varid'>ty</span>
</pre>\end{code}


%************************************************************************
%*									*
		Predicates
%*									*
%************************************************************************

\begin{code}
<pre><a name="line-1"></a><a name="isImmutableTyVar"></a><span class='hs-definition'>isImmutableTyVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-2"></a>
<a name="line-3"></a><span class='hs-definition'>isImmutableTyVar</span> <span class='hs-varid'>tv</span>
<a name="line-4"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isSkolemTyVar</span> <span class='hs-varid'>tv</span>
<a name="line-5"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-6"></a>
<a name="line-7"></a><a name="isTyConableTyVar"></a><span class='hs-definition'>isTyConableTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isSkolemTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isExistentialTyVar</span><span class='hs-layout'>,</span> 
<a name="line-8"></a>  <span class='hs-varid'>isBoxyTyVar</span><span class='hs-layout'>,</span> <span class='hs-varid'>isMetaTyVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcTyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span> 
<a name="line-9"></a>
<a name="line-10"></a><span class='hs-definition'>isTyConableTyVar</span> <span class='hs-varid'>tv</span>	
<a name="line-11"></a>	<span class='hs-comment'>-- True of a meta-type variable that can be filled in </span>
<a name="line-12"></a>	<span class='hs-comment'>-- with a type constructor application; in particular,</span>
<a name="line-13"></a>	<span class='hs-comment'>-- not a SigTv</span>
<a name="line-14"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span> 
<a name="line-15"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-16"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-conid'>BoxTv</span>      <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-17"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-conid'>TauTv</span>      <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-18"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigTv</span> <span class='hs-layout'>{</span><span class='hs-layout'>}</span><span class='hs-layout'>)</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-19"></a>	<span class='hs-conid'>SkolemTv</span> <span class='hs-layout'>{</span><span class='hs-layout'>}</span>	    <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-20"></a>	
<a name="line-21"></a><a name="isSkolemTyVar"></a><span class='hs-definition'>isSkolemTyVar</span> <span class='hs-varid'>tv</span> 
<a name="line-22"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT2</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>,</span> <span class='hs-varid'>ppr</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-23"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-24"></a>	<span class='hs-conid'>SkolemTv</span> <span class='hs-keyword'>_</span>         <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-25"></a> 	<span class='hs-conid'>MetaTv</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span>         <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-26"></a>
<a name="line-27"></a><a name="isExistentialTyVar"></a><span class='hs-definition'>isExistentialTyVar</span> <span class='hs-varid'>tv</span> 	<span class='hs-comment'>-- Existential type variable, bound by a pattern</span>
<a name="line-28"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-29"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-30"></a>	<span class='hs-conid'>SkolemTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>PatSkol</span> <span class='hs-layout'>{</span><span class='hs-layout'>}</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-31"></a>	<span class='hs-keyword'>_</span>                     <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-32"></a>
<a name="line-33"></a><a name="isMetaTyVar"></a><span class='hs-definition'>isMetaTyVar</span> <span class='hs-varid'>tv</span> 
<a name="line-34"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT2</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>,</span> <span class='hs-varid'>ppr</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-35"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-36"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-37"></a>	<span class='hs-keyword'>_</span>          <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-38"></a>
<a name="line-39"></a><a name="isBoxyTyVar"></a><span class='hs-definition'>isBoxyTyVar</span> <span class='hs-varid'>tv</span> 
<a name="line-40"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-41"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-42"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-conid'>BoxTv</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-43"></a>	<span class='hs-keyword'>_</span>              <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-44"></a>
<a name="line-45"></a><a name="isSigTyVar"></a><span class='hs-definition'>isSigTyVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Var</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-46"></a><span class='hs-definition'>isSigTyVar</span> <span class='hs-varid'>tv</span> 
<a name="line-47"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-48"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-49"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-layout'>(</span><span class='hs-conid'>SigTv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-50"></a>	<span class='hs-keyword'>_</span>                  <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-51"></a>
<a name="line-52"></a><a name="metaTvRef"></a><span class='hs-definition'>metaTvRef</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>IORef</span> <span class='hs-conid'>MetaDetails</span>
<a name="line-53"></a><span class='hs-definition'>metaTvRef</span> <span class='hs-varid'>tv</span> 
<a name="line-54"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT2</span><span class='hs-layout'>(</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>,</span> <span class='hs-varid'>ppr</span> <span class='hs-varid'>tv</span> <span class='hs-layout'>)</span>
<a name="line-55"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>of</span>
<a name="line-56"></a>	<span class='hs-conid'>MetaTv</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>ref</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>ref</span>
<a name="line-57"></a>	<span class='hs-keyword'>_</span>          <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"metaTvRef"</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>
<a name="line-58"></a>
<a name="line-59"></a><a name="isFlexi"></a><span class='hs-definition'>isFlexi</span><span class='hs-layout'>,</span> <span class='hs-varid'>isIndirect</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>MetaDetails</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-60"></a><span class='hs-definition'>isFlexi</span> <span class='hs-conid'>Flexi</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-61"></a><span class='hs-definition'>isFlexi</span> <span class='hs-keyword'>_</span>     <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-62"></a>
<a name="line-63"></a><a name="isIndirect"></a><span class='hs-definition'>isIndirect</span> <span class='hs-layout'>(</span><span class='hs-conid'>Indirect</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-64"></a><span class='hs-definition'>isIndirect</span> <span class='hs-keyword'>_</span>            <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-65"></a>
<a name="line-66"></a><a name="isRuntimeUnk"></a><span class='hs-definition'>isRuntimeUnk</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-67"></a><span class='hs-definition'>isRuntimeUnk</span> <span class='hs-varid'>x</span> <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>x</span>
<a name="line-68"></a>               <span class='hs-layout'>,</span> <span class='hs-conid'>SkolemTv</span> <span class='hs-conid'>RuntimeUnkSkol</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>x</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-69"></a>               <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-70"></a>
<a name="line-71"></a><a name="isUnk"></a><span class='hs-definition'>isUnk</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-72"></a><span class='hs-definition'>isUnk</span> <span class='hs-varid'>x</span> <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>x</span>
<a name="line-73"></a>        <span class='hs-layout'>,</span> <span class='hs-conid'>SkolemTv</span> <span class='hs-conid'>UnkSkol</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcTyVarDetails</span> <span class='hs-varid'>x</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-74"></a>        <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
</pre>\end{code}


%************************************************************************
%*									*
\subsection{Tau, sigma and rho}
%*									*
%************************************************************************

\begin{code}
<pre><a name="line-1"></a><a name="mkSigmaTy"></a><span class='hs-definition'>mkSigmaTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>TyVar</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>PredType</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span>
<a name="line-2"></a><span class='hs-definition'>mkSigmaTy</span> <span class='hs-varid'>tyvars</span> <span class='hs-varid'>theta</span> <span class='hs-varid'>tau</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>mkForAllTys</span> <span class='hs-varid'>tyvars</span> <span class='hs-layout'>(</span><span class='hs-varid'>mkPhiTy</span> <span class='hs-varid'>theta</span> <span class='hs-varid'>tau</span><span class='hs-layout'>)</span>
<a name="line-3"></a>
<a name="line-4"></a><a name="mkPhiTy"></a><span class='hs-definition'>mkPhiTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>PredType</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span>
<a name="line-5"></a><span class='hs-definition'>mkPhiTy</span> <span class='hs-varid'>theta</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>foldr</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>\</span><span class='hs-varid'>p</span> <span class='hs-varid'>r</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>mkFunTy</span> <span class='hs-layout'>(</span><span class='hs-varid'>mkPredTy</span> <span class='hs-varid'>p</span><span class='hs-layout'>)</span> <span class='hs-varid'>r</span><span class='hs-layout'>)</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>theta</span>
</pre>\end{code}

@isTauTy@ tests for nested for-alls.  It should not be called on a boxy type.

\begin{code}
<pre><a name="line-1"></a><a name="isTauTy"></a><span class='hs-definition'>isTauTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-2"></a><span class='hs-definition'>isTauTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isTauTy</span> <span class='hs-varid'>ty'</span>
<a name="line-3"></a><span class='hs-definition'>isTauTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>	 <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ASSERT</span><span class='hs-layout'>(</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isBoxyTyVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span> <span class='hs-layout'>)</span>
<a name="line-4"></a>			   <span class='hs-conid'>True</span>
<a name="line-5"></a><span class='hs-definition'>isTauTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tc</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>all</span> <span class='hs-varid'>isTauTy</span> <span class='hs-varid'>tys</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isTauTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-6"></a><span class='hs-definition'>isTauTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>AppTy</span> <span class='hs-varid'>a</span> <span class='hs-varid'>b</span><span class='hs-layout'>)</span>	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isTauTy</span> <span class='hs-varid'>a</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isTauTy</span> <span class='hs-varid'>b</span>
<a name="line-7"></a><span class='hs-definition'>isTauTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>a</span> <span class='hs-varid'>b</span><span class='hs-layout'>)</span>	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isTauTy</span> <span class='hs-varid'>a</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isTauTy</span> <span class='hs-varid'>b</span>
<a name="line-8"></a><span class='hs-definition'>isTauTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>	  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>		<span class='hs-comment'>-- Don't look through source types</span>
<a name="line-9"></a><span class='hs-definition'>isTauTy</span> <span class='hs-keyword'>_</span>    		  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-10"></a>
<a name="line-11"></a>
<a name="line-12"></a><a name="isTauTyCon"></a><span class='hs-definition'>isTauTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-13"></a><span class='hs-comment'>-- Returns False for type synonyms whose expansion is a polytype</span>
<a name="line-14"></a><span class='hs-definition'>isTauTyCon</span> <span class='hs-varid'>tc</span> 
<a name="line-15"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isClosedSynTyCon</span> <span class='hs-varid'>tc</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isTauTy</span> <span class='hs-layout'>(</span><span class='hs-varid'>snd</span> <span class='hs-layout'>(</span><span class='hs-varid'>synTyConDefn</span> <span class='hs-varid'>tc</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>
<a name="line-16"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>           <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-17"></a>
<a name="line-18"></a><a name="isBoxyTy"></a><span class='hs-comment'>---------------</span>
<a name="line-19"></a><span class='hs-definition'>isBoxyTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-20"></a><span class='hs-definition'>isBoxyTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>any</span> <span class='hs-varid'>isBoxyTyVar</span> <span class='hs-layout'>(</span><span class='hs-varid'>varSetElems</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>
<a name="line-21"></a>
<a name="line-22"></a><a name="isRigidTy"></a><span class='hs-definition'>isRigidTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-23"></a><span class='hs-comment'>-- A type is rigid if it has no meta type variables in it</span>
<a name="line-24"></a><span class='hs-definition'>isRigidTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>all</span> <span class='hs-varid'>isImmutableTyVar</span> <span class='hs-layout'>(</span><span class='hs-varid'>varSetElems</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>
<a name="line-25"></a>
<a name="line-26"></a><a name="isRefineableTy"></a><span class='hs-definition'>isRefineableTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>Bool</span><span class='hs-layout'>,</span><span class='hs-conid'>Bool</span><span class='hs-layout'>)</span>
<a name="line-27"></a><span class='hs-comment'>-- A type should have type refinements applied to it if it has</span>
<a name="line-28"></a><span class='hs-comment'>-- free type variables, and they are all rigid</span>
<a name="line-29"></a><span class='hs-definition'>isRefineableTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>null</span> <span class='hs-varid'>tc_tvs</span><span class='hs-layout'>,</span>  <span class='hs-varid'>all</span> <span class='hs-varid'>isImmutableTyVar</span> <span class='hs-varid'>tc_tvs</span><span class='hs-layout'>)</span>
<a name="line-30"></a>		    <span class='hs-keyword'>where</span>
<a name="line-31"></a>		      <span class='hs-varid'>tc_tvs</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>varSetElems</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-32"></a>
<a name="line-33"></a><a name="isRefineablePred"></a><span class='hs-definition'>isRefineablePred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcPredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-34"></a><span class='hs-definition'>isRefineablePred</span> <span class='hs-varid'>pred</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>null</span> <span class='hs-varid'>tc_tvs</span><span class='hs-layout'>)</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>all</span> <span class='hs-varid'>isImmutableTyVar</span> <span class='hs-varid'>tc_tvs</span>
<a name="line-35"></a>		      <span class='hs-keyword'>where</span>
<a name="line-36"></a>		        <span class='hs-varid'>tc_tvs</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>varSetElems</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcTyVarsOfPred</span> <span class='hs-varid'>pred</span><span class='hs-layout'>)</span>
<a name="line-37"></a>
<a name="line-38"></a><a name="getDFunTyKey"></a><span class='hs-comment'>---------------</span>
<a name="line-39"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>OccName</span>	<span class='hs-comment'>-- Get some string from a type, to be used to </span>
<a name="line-40"></a>				<span class='hs-comment'>-- construct a dictionary function name</span>
<a name="line-41"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getDFunTyKey</span> <span class='hs-varid'>ty'</span>
<a name="line-42"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getOccName</span> <span class='hs-varid'>tv</span>
<a name="line-43"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tc</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getOccName</span> <span class='hs-varid'>tc</span>
<a name="line-44"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-layout'>(</span><span class='hs-conid'>AppTy</span> <span class='hs-varid'>fun</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getDFunTyKey</span> <span class='hs-varid'>fun</span>
<a name="line-45"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getOccName</span> <span class='hs-varid'>funTyCon</span>
<a name="line-46"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>t</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getDFunTyKey</span> <span class='hs-varid'>t</span>
<a name="line-47"></a><span class='hs-definition'>getDFunTyKey</span> <span class='hs-varid'>ty</span>		     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"getDFunTyKey"</span> <span class='hs-layout'>(</span><span class='hs-varid'>pprType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-48"></a><span class='hs-comment'>-- PredTy shouldn't happen</span>
</pre>\end{code}


%************************************************************************
%*									*
\subsection{Expanding and splitting}
%*									*
%************************************************************************

These tcSplit functions are like their non-Tc analogues, but
	a) they do not look through newtypes
	b) they do not look through PredTys
	c) [future] they ignore usage-type annotations

However, they are non-monadic and do not follow through mutable type
variables.  It's up to you to make sure this doesn't matter.

\begin{code}
<pre><a name="line-1"></a><a name="tcSplitForAllTys"></a><span class='hs-definition'>tcSplitForAllTys</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>[</span><span class='hs-conid'>TyVar</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-2"></a><span class='hs-definition'>tcSplitForAllTys</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>split</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>ty</span> <span class='hs-conid'>[]</span>
<a name="line-3"></a>   <span class='hs-keyword'>where</span>
<a name="line-4"></a>     <span class='hs-varid'>split</span> <span class='hs-varid'>orig_ty</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>tvs</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>split</span> <span class='hs-varid'>orig_ty</span> <span class='hs-varid'>ty'</span> <span class='hs-varid'>tvs</span>
<a name="line-5"></a>     <span class='hs-varid'>split</span> <span class='hs-keyword'>_</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-varid'>tv</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-varid'>tvs</span> 
<a name="line-6"></a>       <span class='hs-keyglyph'>|</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isCoVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>split</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>ty</span> <span class='hs-layout'>(</span><span class='hs-varid'>tv</span><span class='hs-conop'>:</span><span class='hs-varid'>tvs</span><span class='hs-layout'>)</span>
<a name="line-7"></a>     <span class='hs-varid'>split</span> <span class='hs-varid'>orig_ty</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tvs</span> <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>reverse</span> <span class='hs-varid'>tvs</span><span class='hs-layout'>,</span> <span class='hs-varid'>orig_ty</span><span class='hs-layout'>)</span>
<a name="line-8"></a>
<a name="line-9"></a><a name="tcIsForAllTy"></a><span class='hs-definition'>tcIsForAllTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-10"></a><span class='hs-definition'>tcIsForAllTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcIsForAllTy</span> <span class='hs-varid'>ty'</span>
<a name="line-11"></a><span class='hs-definition'>tcIsForAllTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isCoVar</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>
<a name="line-12"></a><span class='hs-definition'>tcIsForAllTy</span> <span class='hs-keyword'>_</span>               <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-13"></a>
<a name="line-14"></a><a name="tcSplitPredFunTy_maybe"></a><span class='hs-definition'>tcSplitPredFunTy_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredType</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-15"></a><span class='hs-comment'>-- Split off the first predicate argument from a type</span>
<a name="line-16"></a><span class='hs-definition'>tcSplitPredFunTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitPredFunTy_maybe</span> <span class='hs-varid'>ty'</span>
<a name="line-17"></a><span class='hs-definition'>tcSplitPredFunTy_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-varid'>tv</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-18"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isCoVar</span> <span class='hs-varid'>tv</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>coVarPred</span> <span class='hs-varid'>tv</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-19"></a><span class='hs-definition'>tcSplitPredFunTy_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>
<a name="line-20"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>p</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcSplitPredTy_maybe</span> <span class='hs-varid'>arg</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>p</span><span class='hs-layout'>,</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>
<a name="line-21"></a><span class='hs-definition'>tcSplitPredFunTy_maybe</span> <span class='hs-keyword'>_</span>
<a name="line-22"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-23"></a>
<a name="line-24"></a><a name="tcSplitPhiTy"></a><span class='hs-definition'>tcSplitPhiTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>ThetaType</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-25"></a><span class='hs-definition'>tcSplitPhiTy</span> <span class='hs-varid'>ty</span>
<a name="line-26"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>split</span> <span class='hs-varid'>ty</span> <span class='hs-conid'>[]</span>
<a name="line-27"></a>  <span class='hs-keyword'>where</span>
<a name="line-28"></a>    <span class='hs-varid'>split</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>ts</span> 
<a name="line-29"></a>      <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitPredFunTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-30"></a>	  <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>pred</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>split</span> <span class='hs-varid'>ty</span> <span class='hs-layout'>(</span><span class='hs-varid'>pred</span><span class='hs-conop'>:</span><span class='hs-varid'>ts</span><span class='hs-layout'>)</span>
<a name="line-31"></a>	  <span class='hs-conid'>Nothing</span>         <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>reverse</span> <span class='hs-varid'>ts</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-32"></a>
<a name="line-33"></a><a name="tcSplitSigmaTy"></a><span class='hs-definition'>tcSplitSigmaTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>[</span><span class='hs-conid'>TyVar</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> <span class='hs-conid'>ThetaType</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-34"></a><span class='hs-definition'>tcSplitSigmaTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitForAllTys</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-35"></a>			<span class='hs-layout'>(</span><span class='hs-varid'>tvs</span><span class='hs-layout'>,</span> <span class='hs-varid'>rho</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitPhiTy</span> <span class='hs-varid'>rho</span> <span class='hs-keyword'>of</span>
<a name="line-36"></a>					<span class='hs-layout'>(</span><span class='hs-varid'>theta</span><span class='hs-layout'>,</span> <span class='hs-varid'>tau</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>tvs</span><span class='hs-layout'>,</span> <span class='hs-varid'>theta</span><span class='hs-layout'>,</span> <span class='hs-varid'>tau</span><span class='hs-layout'>)</span>
<a name="line-37"></a>
<a name="line-38"></a><a name="tcMultiSplitSigmaTy"></a><span class='hs-comment'>-----------------------</span>
<a name="line-39"></a><span class='hs-definition'>tcMultiSplitSigmaTy</span>
<a name="line-40"></a>	<span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcSigmaType</span>
<a name="line-41"></a>	<span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span> <span class='hs-keyglyph'>[</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>[</span><span class='hs-conid'>TyVar</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> <span class='hs-conid'>ThetaType</span><span class='hs-layout'>)</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span>	<span class='hs-comment'>-- forall as.C =&gt; forall bs.D</span>
<a name="line-42"></a>	     <span class='hs-conid'>TcSigmaType</span><span class='hs-layout'>)</span>		<span class='hs-comment'>-- The rest of the type</span>
<a name="line-43"></a>
<a name="line-44"></a><span class='hs-comment'>-- We need a loop here because we are now prepared to entertain</span>
<a name="line-45"></a><span class='hs-comment'>-- types like</span>
<a name="line-46"></a><span class='hs-comment'>-- 	f:: forall a. Eq a =&gt; forall b. Baz b =&gt; tau</span>
<a name="line-47"></a><span class='hs-comment'>-- We want to instantiate this to</span>
<a name="line-48"></a><span class='hs-comment'>-- 	f2::tau		{f2 = f1 b (Baz b), f1 = f a (Eq a)}</span>
<a name="line-49"></a>
<a name="line-50"></a><span class='hs-definition'>tcMultiSplitSigmaTy</span> <span class='hs-varid'>sigma</span>
<a name="line-51"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcSplitSigmaTy</span> <span class='hs-varid'>sigma</span><span class='hs-layout'>)</span> <span class='hs-keyword'>of</span>
<a name="line-52"></a>	<span class='hs-layout'>(</span><span class='hs-conid'>[]</span><span class='hs-layout'>,</span> <span class='hs-conid'>[]</span><span class='hs-layout'>,</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>[]</span><span class='hs-layout'>,</span> <span class='hs-varid'>sigma</span><span class='hs-layout'>)</span>
<a name="line-53"></a>	<span class='hs-layout'>(</span><span class='hs-varid'>tvs</span><span class='hs-layout'>,</span> <span class='hs-varid'>theta</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcMultiSplitSigmaTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-54"></a>				<span class='hs-layout'>(</span><span class='hs-varid'>pairs</span><span class='hs-layout'>,</span> <span class='hs-varid'>rest</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-layout'>(</span><span class='hs-varid'>tvs</span><span class='hs-layout'>,</span><span class='hs-varid'>theta</span><span class='hs-layout'>)</span><span class='hs-conop'>:</span><span class='hs-varid'>pairs</span><span class='hs-layout'>,</span> <span class='hs-varid'>rest</span><span class='hs-layout'>)</span>
<a name="line-55"></a>
<a name="line-56"></a><a name="tcTyConAppTyCon"></a><span class='hs-comment'>-----------------------</span>
<a name="line-57"></a><span class='hs-definition'>tcTyConAppTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyCon</span>
<a name="line-58"></a><span class='hs-definition'>tcTyConAppTyCon</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-59"></a>			<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>tc</span>
<a name="line-60"></a>			<span class='hs-conid'>Nothing</span>	     <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"tcTyConAppTyCon"</span> <span class='hs-layout'>(</span><span class='hs-varid'>pprType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-61"></a>
<a name="line-62"></a><a name="tcTyConAppArgs"></a><span class='hs-definition'>tcTyConAppArgs</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span>
<a name="line-63"></a><span class='hs-definition'>tcTyConAppArgs</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-64"></a>			<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-keyword'>_</span><span class='hs-layout'>,</span> <span class='hs-varid'>args</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>args</span>
<a name="line-65"></a>			<span class='hs-conid'>Nothing</span>	       <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"tcTyConAppArgs"</span> <span class='hs-layout'>(</span><span class='hs-varid'>pprType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-66"></a>
<a name="line-67"></a><a name="tcSplitTyConApp"></a><span class='hs-definition'>tcSplitTyConApp</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyCon</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-68"></a><span class='hs-definition'>tcSplitTyConApp</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-69"></a>			<span class='hs-conid'>Just</span> <span class='hs-varid'>stuff</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>stuff</span>
<a name="line-70"></a>			<span class='hs-conid'>Nothing</span>	   <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"tcSplitTyConApp"</span> <span class='hs-layout'>(</span><span class='hs-varid'>pprType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-71"></a>
<a name="line-72"></a><a name="tcSplitTyConApp_maybe"></a><span class='hs-definition'>tcSplitTyConApp_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyCon</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-73"></a><span class='hs-definition'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty'</span>
<a name="line-74"></a><span class='hs-definition'>tcSplitTyConApp_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tc</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>
<a name="line-75"></a><span class='hs-definition'>tcSplitTyConApp_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>funTyCon</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>arg</span><span class='hs-layout'>,</span><span class='hs-varid'>res</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-76"></a>	<span class='hs-comment'>-- Newtypes are opaque, so they may be split</span>
<a name="line-77"></a>	<span class='hs-comment'>-- However, predicates are not treated</span>
<a name="line-78"></a>	<span class='hs-comment'>-- as tycon applications by the type checker</span>
<a name="line-79"></a><span class='hs-definition'>tcSplitTyConApp_maybe</span> <span class='hs-keyword'>_</span>                 <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-80"></a>
<a name="line-81"></a><a name="tcSplitFunTys"></a><span class='hs-comment'>-----------------------</span>
<a name="line-82"></a><span class='hs-definition'>tcSplitFunTys</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-83"></a><span class='hs-definition'>tcSplitFunTys</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitFunTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-84"></a>			<span class='hs-conid'>Nothing</span>	       <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>[]</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-85"></a>			<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>arg</span><span class='hs-layout'>,</span><span class='hs-varid'>res</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>arg</span><span class='hs-conop'>:</span><span class='hs-varid'>args</span><span class='hs-layout'>,</span> <span class='hs-varid'>res'</span><span class='hs-layout'>)</span>
<a name="line-86"></a>				       <span class='hs-keyword'>where</span>
<a name="line-87"></a>					  <span class='hs-layout'>(</span><span class='hs-varid'>args</span><span class='hs-layout'>,</span><span class='hs-varid'>res'</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitFunTys</span> <span class='hs-varid'>res</span>
<a name="line-88"></a>
<a name="line-89"></a><a name="tcSplitFunTy_maybe"></a><span class='hs-definition'>tcSplitFunTy_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-90"></a><span class='hs-definition'>tcSplitFunTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span>           <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitFunTy_maybe</span> <span class='hs-varid'>ty'</span>
<a name="line-91"></a><span class='hs-definition'>tcSplitFunTy_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>|</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isPredTy</span> <span class='hs-varid'>arg</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>arg</span><span class='hs-layout'>,</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>
<a name="line-92"></a><span class='hs-definition'>tcSplitFunTy_maybe</span> <span class='hs-keyword'>_</span>                                    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-93"></a>	<span class='hs-comment'>-- Note the (not (isPredTy arg)) guard</span>
<a name="line-94"></a>	<span class='hs-comment'>-- Consider	(?x::Int) =&gt; Bool</span>
<a name="line-95"></a>	<span class='hs-comment'>-- We don't want to treat this as a function type!</span>
<a name="line-96"></a>	<span class='hs-comment'>-- A concrete example is test tc230:</span>
<a name="line-97"></a>	<span class='hs-comment'>--	f :: () -&gt; (?p :: ()) =&gt; () -&gt; ()</span>
<a name="line-98"></a>	<span class='hs-comment'>--</span>
<a name="line-99"></a>	<span class='hs-comment'>--	g = f () ()</span>
<a name="line-100"></a>
<a name="line-101"></a><a name="tcSplitFunTysN"></a><span class='hs-definition'>tcSplitFunTysN</span>
<a name="line-102"></a>	<span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcRhoType</span> 
<a name="line-103"></a>	<span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Arity</span>		<span class='hs-comment'>-- N: Number of desired args</span>
<a name="line-104"></a>	<span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>[</span><span class='hs-conid'>TcSigmaType</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> 	<span class='hs-comment'>-- Arg types (N or fewer)</span>
<a name="line-105"></a>	    <span class='hs-conid'>TcSigmaType</span><span class='hs-layout'>)</span>	<span class='hs-comment'>-- The rest of the type</span>
<a name="line-106"></a>
<a name="line-107"></a><span class='hs-definition'>tcSplitFunTysN</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>n_args</span>
<a name="line-108"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>n_args</span> <span class='hs-varop'>==</span> <span class='hs-num'>0</span>
<a name="line-109"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-conid'>[]</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-110"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>arg</span><span class='hs-layout'>,</span><span class='hs-varid'>res</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcSplitFunTy_maybe</span> <span class='hs-varid'>ty</span>
<a name="line-111"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitFunTysN</span> <span class='hs-varid'>res</span> <span class='hs-layout'>(</span><span class='hs-varid'>n_args</span> <span class='hs-comment'>-</span> <span class='hs-num'>1</span><span class='hs-layout'>)</span> <span class='hs-keyword'>of</span>
<a name="line-112"></a>	<span class='hs-layout'>(</span><span class='hs-varid'>args</span><span class='hs-layout'>,</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>arg</span><span class='hs-conop'>:</span><span class='hs-varid'>args</span><span class='hs-layout'>,</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>
<a name="line-113"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>
<a name="line-114"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-conid'>[]</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-115"></a>
<a name="line-116"></a><a name="tcSplitFunTy"></a><span class='hs-definition'>tcSplitFunTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-117"></a><span class='hs-definition'>tcSplitFunTy</span>  <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>expectJust</span> <span class='hs-str'>"tcSplitFunTy"</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcSplitFunTy_maybe</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-118"></a>
<a name="line-119"></a><a name="tcFunArgTy"></a><span class='hs-definition'>tcFunArgTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span>
<a name="line-120"></a><span class='hs-definition'>tcFunArgTy</span>    <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>fst</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcSplitFunTy</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-121"></a>
<a name="line-122"></a><a name="tcFunResultTy"></a><span class='hs-definition'>tcFunResultTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span>
<a name="line-123"></a><span class='hs-definition'>tcFunResultTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>snd</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcSplitFunTy</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-124"></a>
<a name="line-125"></a><a name="tcSplitAppTy_maybe"></a><span class='hs-comment'>-----------------------</span>
<a name="line-126"></a><span class='hs-definition'>tcSplitAppTy_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-127"></a><span class='hs-definition'>tcSplitAppTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitAppTy_maybe</span> <span class='hs-varid'>ty'</span>
<a name="line-128"></a><span class='hs-definition'>tcSplitAppTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>repSplitAppTy_maybe</span> <span class='hs-varid'>ty</span>
<a name="line-129"></a>
<a name="line-130"></a><a name="tcSplitAppTy"></a><span class='hs-definition'>tcSplitAppTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>)</span>
<a name="line-131"></a><span class='hs-definition'>tcSplitAppTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitAppTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-132"></a>		    <span class='hs-conid'>Just</span> <span class='hs-varid'>stuff</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>stuff</span>
<a name="line-133"></a>		    <span class='hs-conid'>Nothing</span>    <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"tcSplitAppTy"</span> <span class='hs-layout'>(</span><span class='hs-varid'>pprType</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-134"></a>
<a name="line-135"></a><a name="tcSplitAppTys"></a><span class='hs-definition'>tcSplitAppTys</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-136"></a><span class='hs-definition'>tcSplitAppTys</span> <span class='hs-varid'>ty</span>
<a name="line-137"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty</span> <span class='hs-conid'>[]</span>
<a name="line-138"></a>  <span class='hs-keyword'>where</span>
<a name="line-139"></a>    <span class='hs-varid'>go</span> <span class='hs-varid'>ty</span> <span class='hs-varid'>args</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitAppTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-140"></a>		   <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>ty'</span><span class='hs-layout'>,</span> <span class='hs-varid'>arg</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty'</span> <span class='hs-layout'>(</span><span class='hs-varid'>arg</span><span class='hs-conop'>:</span><span class='hs-varid'>args</span><span class='hs-layout'>)</span>
<a name="line-141"></a>		   <span class='hs-conid'>Nothing</span>	   <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>ty</span><span class='hs-layout'>,</span><span class='hs-varid'>args</span><span class='hs-layout'>)</span>
<a name="line-142"></a>
<a name="line-143"></a><a name="tcGetTyVar_maybe"></a><span class='hs-comment'>-----------------------</span>
<a name="line-144"></a><span class='hs-definition'>tcGetTyVar_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-conid'>TyVar</span>
<a name="line-145"></a><span class='hs-definition'>tcGetTyVar_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcGetTyVar_maybe</span> <span class='hs-varid'>ty'</span>
<a name="line-146"></a><span class='hs-definition'>tcGetTyVar_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>tv</span>
<a name="line-147"></a><span class='hs-definition'>tcGetTyVar_maybe</span> <span class='hs-keyword'>_</span>              <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-148"></a>
<a name="line-149"></a><a name="tcGetTyVar"></a><span class='hs-definition'>tcGetTyVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>String</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyVar</span>
<a name="line-150"></a><span class='hs-definition'>tcGetTyVar</span> <span class='hs-varid'>msg</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>expectJust</span> <span class='hs-varid'>msg</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcGetTyVar_maybe</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-151"></a>
<a name="line-152"></a><a name="tcIsTyVarTy"></a><span class='hs-definition'>tcIsTyVarTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-153"></a><span class='hs-definition'>tcIsTyVarTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>maybeToBool</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcGetTyVar_maybe</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-154"></a>
<a name="line-155"></a><a name="tcSplitDFunTy"></a><span class='hs-comment'>-----------------------</span>
<a name="line-156"></a><span class='hs-definition'>tcSplitDFunTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>[</span><span class='hs-conid'>TyVar</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>PredType</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>,</span> <span class='hs-conid'>Class</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-157"></a><span class='hs-comment'>-- Split the type of a dictionary function</span>
<a name="line-158"></a><span class='hs-definition'>tcSplitDFunTy</span> <span class='hs-varid'>ty</span> 
<a name="line-159"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitSigmaTy</span> <span class='hs-varid'>ty</span>   <span class='hs-keyword'>of</span> <span class='hs-layout'>{</span> <span class='hs-layout'>(</span><span class='hs-varid'>tvs</span><span class='hs-layout'>,</span> <span class='hs-varid'>theta</span><span class='hs-layout'>,</span> <span class='hs-varid'>tau</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span>
<a name="line-160"></a>    <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitDFunHead</span> <span class='hs-varid'>tau</span> <span class='hs-keyword'>of</span> <span class='hs-layout'>{</span> <span class='hs-layout'>(</span><span class='hs-varid'>clas</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> 
<a name="line-161"></a>    <span class='hs-layout'>(</span><span class='hs-varid'>tvs</span><span class='hs-layout'>,</span> <span class='hs-varid'>theta</span><span class='hs-layout'>,</span> <span class='hs-varid'>clas</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-layout'>}</span><span class='hs-layout'>}</span>
<a name="line-162"></a>
<a name="line-163"></a><a name="tcSplitDFunHead"></a><span class='hs-definition'>tcSplitDFunHead</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>Class</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-164"></a><span class='hs-definition'>tcSplitDFunHead</span> <span class='hs-varid'>tau</span>  
<a name="line-165"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitPredTy_maybe</span> <span class='hs-varid'>tau</span> <span class='hs-keyword'>of</span> 
<a name="line-166"></a>	<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>clas</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>
<a name="line-167"></a>	<span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>panic</span> <span class='hs-str'>"tcSplitDFunHead"</span>
<a name="line-168"></a>
<a name="line-169"></a><a name="tcInstHeadTyNotSynonym"></a><span class='hs-definition'>tcInstHeadTyNotSynonym</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-170"></a><span class='hs-comment'>-- Used in Haskell-98 mode, for the argument types of an instance head</span>
<a name="line-171"></a><span class='hs-comment'>-- These must not be type synonyms, but everywhere else type synonyms</span>
<a name="line-172"></a><span class='hs-comment'>-- are transparent, so we need a special function here</span>
<a name="line-173"></a><span class='hs-definition'>tcInstHeadTyNotSynonym</span> <span class='hs-varid'>ty</span>
<a name="line-174"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-175"></a>        <span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tc</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isSynTyCon</span> <span class='hs-varid'>tc</span><span class='hs-layout'>)</span>
<a name="line-176"></a>        <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span>
<a name="line-177"></a>
<a name="line-178"></a><a name="tcInstHeadTyAppAllTyVars"></a><span class='hs-definition'>tcInstHeadTyAppAllTyVars</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-179"></a><span class='hs-comment'>-- Used in Haskell-98 mode, for the argument types of an instance head</span>
<a name="line-180"></a><span class='hs-comment'>-- These must be a constructor applied to type variable arguments</span>
<a name="line-181"></a><span class='hs-definition'>tcInstHeadTyAppAllTyVars</span> <span class='hs-varid'>ty</span>
<a name="line-182"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-183"></a>	<span class='hs-conid'>TyConApp</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tys</span>  <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>ok</span> <span class='hs-varid'>tys</span>
<a name="line-184"></a>	<span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span>   <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>ok</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>arg</span><span class='hs-layout'>,</span> <span class='hs-varid'>res</span><span class='hs-keyglyph'>]</span>
<a name="line-185"></a>	<span class='hs-keyword'>_</span>               <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-186"></a>  <span class='hs-keyword'>where</span>
<a name="line-187"></a>	<span class='hs-comment'>-- Check that all the types are type variables,</span>
<a name="line-188"></a>	<span class='hs-comment'>-- and that each is distinct</span>
<a name="line-189"></a>    <span class='hs-varid'>ok</span> <span class='hs-varid'>tys</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>equalLength</span> <span class='hs-varid'>tvs</span> <span class='hs-varid'>tys</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>hasNoDups</span> <span class='hs-varid'>tvs</span>
<a name="line-190"></a>	   <span class='hs-keyword'>where</span>
<a name="line-191"></a>	     <span class='hs-varid'>tvs</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>mapCatMaybes</span> <span class='hs-varid'>get_tv</span> <span class='hs-varid'>tys</span>
<a name="line-192"></a>
<a name="line-193"></a>    <span class='hs-varid'>get_tv</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>tv</span>	<span class='hs-comment'>-- through synonyms</span>
<a name="line-194"></a>    <span class='hs-varid'>get_tv</span> <span class='hs-keyword'>_</span>             <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
</pre>\end{code}



%************************************************************************
%*									*
\subsection{Predicate types}
%*									*
%************************************************************************

\begin{code}
<pre><a name="line-1"></a><a name="tcSplitPredTy_maybe"></a><span class='hs-definition'>tcSplitPredTy_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-conid'>PredType</span>
<a name="line-2"></a>   <span class='hs-comment'>-- Returns Just for predicates only</span>
<a name="line-3"></a><span class='hs-definition'>tcSplitPredTy_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitPredTy_maybe</span> <span class='hs-varid'>ty'</span>
<a name="line-4"></a><span class='hs-definition'>tcSplitPredTy_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-varid'>p</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>p</span>
<a name="line-5"></a><span class='hs-definition'>tcSplitPredTy_maybe</span> <span class='hs-keyword'>_</span>             <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-6"></a>
<a name="line-7"></a><a name="predTyUnique"></a><span class='hs-definition'>predTyUnique</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Unique</span>
<a name="line-8"></a><span class='hs-definition'>predTyUnique</span> <span class='hs-layout'>(</span><span class='hs-conid'>IParam</span> <span class='hs-varid'>n</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getUnique</span> <span class='hs-layout'>(</span><span class='hs-varid'>ipNameName</span> <span class='hs-varid'>n</span><span class='hs-layout'>)</span>
<a name="line-9"></a><span class='hs-definition'>predTyUnique</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-varid'>clas</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getUnique</span> <span class='hs-varid'>clas</span>
<a name="line-10"></a><span class='hs-definition'>predTyUnique</span> <span class='hs-layout'>(</span><span class='hs-conid'>EqPred</span> <span class='hs-varid'>a</span> <span class='hs-varid'>b</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>pprPanic</span> <span class='hs-str'>"predTyUnique"</span> <span class='hs-layout'>(</span><span class='hs-varid'>ppr</span> <span class='hs-layout'>(</span><span class='hs-conid'>EqPred</span> <span class='hs-varid'>a</span> <span class='hs-varid'>b</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>
</pre>\end{code}


--------------------- Dictionary types ---------------------------------

\begin{code}
<pre><a name="line-1"></a><a name="mkClassPred"></a><span class='hs-definition'>mkClassPred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Class</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>PredType</span>
<a name="line-2"></a><span class='hs-definition'>mkClassPred</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>ClassP</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span>
<a name="line-3"></a>
<a name="line-4"></a><a name="isClassPred"></a><span class='hs-definition'>isClassPred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-5"></a><span class='hs-definition'>isClassPred</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-6"></a><span class='hs-definition'>isClassPred</span> <span class='hs-keyword'>_</span>            <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-7"></a>
<a name="line-8"></a><a name="isTyVarClassPred"></a><span class='hs-definition'>isTyVarClassPred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-9"></a><span class='hs-definition'>isTyVarClassPred</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>all</span> <span class='hs-varid'>tcIsTyVarTy</span> <span class='hs-varid'>tys</span>
<a name="line-10"></a><span class='hs-definition'>isTyVarClassPred</span> <span class='hs-keyword'>_</span>              <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-11"></a>
<a name="line-12"></a><a name="getClassPredTys_maybe"></a><span class='hs-definition'>getClassPredTys_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>Class</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-13"></a><span class='hs-definition'>getClassPredTys_maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>clas</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>
<a name="line-14"></a><span class='hs-definition'>getClassPredTys_maybe</span> <span class='hs-keyword'>_</span>                 <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-15"></a>
<a name="line-16"></a><a name="getClassPredTys"></a><span class='hs-definition'>getClassPredTys</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-conid'>Class</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span>
<a name="line-17"></a><span class='hs-definition'>getClassPredTys</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>clas</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>
<a name="line-18"></a><span class='hs-definition'>getClassPredTys</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>panic</span> <span class='hs-str'>"getClassPredTys"</span>
<a name="line-19"></a>
<a name="line-20"></a><a name="mkDictTy"></a><span class='hs-definition'>mkDictTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Class</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span>
<a name="line-21"></a><span class='hs-definition'>mkDictTy</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>mkPredTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-varid'>clas</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>
<a name="line-22"></a>
<a name="line-23"></a><a name="isDictTy"></a><span class='hs-definition'>isDictTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-24"></a><span class='hs-definition'>isDictTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isDictTy</span> <span class='hs-varid'>ty'</span>
<a name="line-25"></a><span class='hs-definition'>isDictTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-varid'>p</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isClassPred</span> <span class='hs-varid'>p</span>
<a name="line-26"></a><span class='hs-definition'>isDictTy</span> <span class='hs-keyword'>_</span>          <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-27"></a>
<a name="line-28"></a><a name="isDictLikeTy"></a><span class='hs-definition'>isDictLikeTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-29"></a><span class='hs-comment'>-- Note [Dictionary-like types]</span>
<a name="line-30"></a><span class='hs-definition'>isDictLikeTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isDictTy</span> <span class='hs-varid'>ty'</span>
<a name="line-31"></a><span class='hs-definition'>isDictLikeTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-varid'>p</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isClassPred</span> <span class='hs-varid'>p</span>
<a name="line-32"></a><span class='hs-definition'>isDictLikeTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tc</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> 
<a name="line-33"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isTupleTyCon</span> <span class='hs-varid'>tc</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>all</span> <span class='hs-varid'>isDictLikeTy</span> <span class='hs-varid'>tys</span>
<a name="line-34"></a><span class='hs-definition'>isDictLikeTy</span> <span class='hs-keyword'>_</span>          <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
</pre>\end{code}

Note [Dictionary-like types]
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Being "dictionary-like" means either a dictionary type or a tuple thereof.
In GHC 6.10 we build implication constraints which construct such tuples,
and if we land up with a binding
    t :: (C [a], Eq [a])
    t = blah
then we want to treat t as cheap under "-fdicts-cheap" for example.
(Implication constraints are normally inlined, but sadly not if the
occurrence is itself inside an INLINE function!  Until we revise the 
handling of implication constraints, that is.)  This turned out to
be important in getting good arities in DPH code.  Example:

    class C a
    class D a where { foo :: a -> a }
    instance C a => D (Maybe a) where { foo x = x }

    bar :: (C a, C b) => a -> b -> (Maybe a, Maybe b)
    {-# INLINE bar #-}
    bar x y = (foo (Just x), foo (Just y))

Then 'bar' should jolly well have arity 4 (two dicts, two args), but
we ended up with something like
   bar = __inline_me__ (\d1,d2. let t :: (D (Maybe a), D (Maybe b)) = ...
                                in \x,y. <blah>)

This is all a bit ad-hoc; eg it relies on knowing that implication
constraints build tuples.

--------------------- Implicit parameters ---------------------------------

\begin{code}
<pre><a name="line-1"></a><a name="isIPPred"></a><span class='hs-definition'>isIPPred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-2"></a><span class='hs-definition'>isIPPred</span> <span class='hs-layout'>(</span><span class='hs-conid'>IParam</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-3"></a><span class='hs-definition'>isIPPred</span> <span class='hs-keyword'>_</span>            <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-4"></a>
<a name="line-5"></a><a name="isInheritablePred"></a><span class='hs-definition'>isInheritablePred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-6"></a><span class='hs-comment'>-- Can be inherited by a context.  For example, consider</span>
<a name="line-7"></a><span class='hs-comment'>--	f x = let g y = (?v, y+x)</span>
<a name="line-8"></a><span class='hs-comment'>--	      in (g 3 with ?v = 8, </span>
<a name="line-9"></a><span class='hs-comment'>--		  g 4 with ?v = 9)</span>
<a name="line-10"></a><span class='hs-comment'>-- The point is that g's type must be quantifed over ?v:</span>
<a name="line-11"></a><span class='hs-comment'>--	g :: (?v :: a) =&gt; a -&gt; a</span>
<a name="line-12"></a><span class='hs-comment'>-- but it doesn't need to be quantified over the Num a dictionary</span>
<a name="line-13"></a><span class='hs-comment'>-- which can be free in g's rhs, and shared by both calls to g</span>
<a name="line-14"></a><span class='hs-definition'>isInheritablePred</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-15"></a><span class='hs-definition'>isInheritablePred</span> <span class='hs-layout'>(</span><span class='hs-conid'>EqPred</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-16"></a><span class='hs-definition'>isInheritablePred</span> <span class='hs-keyword'>_</span>            <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
</pre>\end{code}

--------------------- Equality predicates ---------------------------------
\begin{code}
<pre><a name="line-1"></a><a name="substEqSpec"></a><span class='hs-definition'>substEqSpec</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TvSubst</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyglyph'>[</span><span class='hs-layout'>(</span><span class='hs-conid'>TyVar</span><span class='hs-layout'>,</span><span class='hs-conid'>Type</span><span class='hs-layout'>)</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyglyph'>[</span><span class='hs-layout'>(</span><span class='hs-conid'>TcType</span><span class='hs-layout'>,</span><span class='hs-conid'>TcType</span><span class='hs-layout'>)</span><span class='hs-keyglyph'>]</span>
<a name="line-2"></a><span class='hs-definition'>substEqSpec</span> <span class='hs-varid'>subst</span> <span class='hs-varid'>eq_spec</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyglyph'>[</span> <span class='hs-layout'>(</span><span class='hs-varid'>substTyVar</span> <span class='hs-varid'>subst</span> <span class='hs-varid'>tv</span><span class='hs-layout'>,</span> <span class='hs-varid'>substTy</span> <span class='hs-varid'>subst</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>
<a name="line-3"></a>			    <span class='hs-keyglyph'>|</span> <span class='hs-layout'>(</span><span class='hs-varid'>tv</span><span class='hs-layout'>,</span><span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>eq_spec</span><span class='hs-keyglyph'>]</span>
</pre>\end{code}


%************************************************************************
%*									*
\subsection{Predicates}
%*									*
%************************************************************************

isSigmaTy returns true of any qualified type.  It doesn't *necessarily* have 
any foralls.  E.g.
	f :: (?x::Int) => Int -> Int

\begin{code}
<pre><a name="line-1"></a><a name="isSigmaTy"></a><span class='hs-definition'>isSigmaTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-2"></a><span class='hs-definition'>isSigmaTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isSigmaTy</span> <span class='hs-varid'>ty'</span>
<a name="line-3"></a><span class='hs-definition'>isSigmaTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-4"></a><span class='hs-definition'>isSigmaTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>a</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isPredTy</span> <span class='hs-varid'>a</span>
<a name="line-5"></a><span class='hs-definition'>isSigmaTy</span> <span class='hs-keyword'>_</span>              <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-6"></a>
<a name="line-7"></a><a name="isOverloadedTy"></a><span class='hs-definition'>isOverloadedTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-8"></a><span class='hs-comment'>-- Yes for a type of a function that might require evidence-passing</span>
<a name="line-9"></a><span class='hs-comment'>-- Used only by bindInstsOfLocalFuns/Pats</span>
<a name="line-10"></a><span class='hs-comment'>-- NB: be sure to check for type with an equality predicate; hence isCoVar</span>
<a name="line-11"></a><span class='hs-definition'>isOverloadedTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isOverloadedTy</span> <span class='hs-varid'>ty'</span>
<a name="line-12"></a><span class='hs-definition'>isOverloadedTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-varid'>tv</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isCoVar</span> <span class='hs-varid'>tv</span> <span class='hs-varop'>||</span> <span class='hs-varid'>isOverloadedTy</span> <span class='hs-varid'>ty</span>
<a name="line-13"></a><span class='hs-definition'>isOverloadedTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>a</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>      <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isPredTy</span> <span class='hs-varid'>a</span>
<a name="line-14"></a><span class='hs-definition'>isOverloadedTy</span> <span class='hs-keyword'>_</span>                <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-15"></a>
<a name="line-16"></a><a name="isPredTy"></a><span class='hs-definition'>isPredTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>	<span class='hs-comment'>-- Belongs in TcType because it does </span>
<a name="line-17"></a>				<span class='hs-comment'>-- not look through newtypes, or predtypes (of course)</span>
<a name="line-18"></a><span class='hs-definition'>isPredTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isPredTy</span> <span class='hs-varid'>ty'</span>
<a name="line-19"></a><span class='hs-definition'>isPredTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-20"></a><span class='hs-definition'>isPredTy</span> <span class='hs-keyword'>_</span>          <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
</pre>\end{code}

\begin{code}
<pre><a name="line-1"></a><a name="isFloatTy"></a><span class='hs-definition'>isFloatTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isDoubleTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isIntegerTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isIntTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isWordTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isBoolTy</span><span class='hs-layout'>,</span>
<a name="line-2"></a>    <span class='hs-varid'>isUnitTy</span><span class='hs-layout'>,</span> <span class='hs-varid'>isCharTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-3"></a><span class='hs-definition'>isFloatTy</span>      <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>floatTyConKey</span>
<a name="line-4"></a><a name="isDoubleTy"></a><span class='hs-definition'>isDoubleTy</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>doubleTyConKey</span>
<a name="line-5"></a><a name="isIntegerTy"></a><span class='hs-definition'>isIntegerTy</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>integerTyConKey</span>
<a name="line-6"></a><a name="isIntTy"></a><span class='hs-definition'>isIntTy</span>        <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>intTyConKey</span>
<a name="line-7"></a><a name="isWordTy"></a><span class='hs-definition'>isWordTy</span>       <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>wordTyConKey</span>
<a name="line-8"></a><a name="isBoolTy"></a><span class='hs-definition'>isBoolTy</span>       <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>boolTyConKey</span>
<a name="line-9"></a><a name="isUnitTy"></a><span class='hs-definition'>isUnitTy</span>       <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>unitTyConKey</span>
<a name="line-10"></a><a name="isCharTy"></a><span class='hs-definition'>isCharTy</span>       <span class='hs-keyglyph'>=</span> <span class='hs-varid'>is_tc</span> <span class='hs-varid'>charTyConKey</span>
<a name="line-11"></a>
<a name="line-12"></a><a name="isStringTy"></a><span class='hs-definition'>isStringTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-13"></a><span class='hs-definition'>isStringTy</span> <span class='hs-varid'>ty</span>
<a name="line-14"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-15"></a>      <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>arg_ty</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>==</span> <span class='hs-varid'>listTyCon</span> <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isCharTy</span> <span class='hs-varid'>arg_ty</span>
<a name="line-16"></a>      <span class='hs-keyword'>_</span>                   <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-17"></a>
<a name="line-18"></a><a name="is_tc"></a><span class='hs-definition'>is_tc</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Unique</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-19"></a><span class='hs-comment'>-- Newtypes are opaque to this</span>
<a name="line-20"></a><span class='hs-definition'>is_tc</span> <span class='hs-varid'>uniq</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-21"></a>			<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>uniq</span> <span class='hs-varop'>==</span> <span class='hs-varid'>getUnique</span> <span class='hs-varid'>tc</span>
<a name="line-22"></a>			<span class='hs-conid'>Nothing</span>	     <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
</pre>\end{code}

\begin{code}
<pre><a name="line-1"></a><a name="isOpenSynTyConApp"></a><span class='hs-comment'>-- NB: Currently used in places where we have already expanded type synonyms;</span>
<a name="line-2"></a><span class='hs-comment'>--     hence no 'coreView'.  This could, however, be changed without breaking</span>
<a name="line-3"></a><span class='hs-comment'>--     any code.</span>
<a name="line-4"></a><span class='hs-definition'>isOpenSynTyConApp</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcTauType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-5"></a><span class='hs-definition'>isOpenSynTyConApp</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tc</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isOpenSynTyCon</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>&amp;&amp;</span> 
<a name="line-6"></a>                                      <span class='hs-varid'>length</span> <span class='hs-varid'>tys</span> <span class='hs-varop'>==</span> <span class='hs-varid'>tyConArity</span> <span class='hs-varid'>tc</span> 
<a name="line-7"></a><span class='hs-definition'>isOpenSynTyConApp</span> <span class='hs-sel'>_other</span>            <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
</pre>\end{code}


%************************************************************************
%*									*
\subsection{Misc}
%*									*
%************************************************************************

\begin{code}
<pre><a name="line-1"></a><a name="deNoteType"></a><span class='hs-definition'>deNoteType</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span>
<a name="line-2"></a><span class='hs-comment'>-- Remove all *outermost* type synonyms and other notes</span>
<a name="line-3"></a><span class='hs-definition'>deNoteType</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>deNoteType</span> <span class='hs-varid'>ty'</span>
<a name="line-4"></a><span class='hs-definition'>deNoteType</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>ty</span>
</pre>\end{code}

\begin{code}
<pre><a name="line-1"></a><a name="tcTyVarsOfType"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TcTyVarSet</span>
<a name="line-2"></a><span class='hs-comment'>-- Just the *TcTyVars* free in the type</span>
<a name="line-3"></a><span class='hs-comment'>-- (Types.tyVarsOfTypes finds all free TyVars)</span>
<a name="line-4"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>if</span> <span class='hs-varid'>isTcTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-keyword'>then</span> <span class='hs-varid'>unitVarSet</span> <span class='hs-varid'>tv</span>
<a name="line-5"></a>						      <span class='hs-keyword'>else</span> <span class='hs-varid'>emptyVarSet</span>
<a name="line-6"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfTypes</span> <span class='hs-varid'>tys</span>
<a name="line-7"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-varid'>sty</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfPred</span> <span class='hs-varid'>sty</span>
<a name="line-8"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>arg</span> <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>res</span>
<a name="line-9"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>AppTy</span> <span class='hs-varid'>fun</span> <span class='hs-varid'>arg</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>fun</span> <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>arg</span>
<a name="line-10"></a><span class='hs-definition'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-varid'>tyvar</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty</span> <span class='hs-varop'>`delVarSet`</span> <span class='hs-varid'>tyvar</span><span class='hs-layout'>)</span>
<a name="line-11"></a>                                      <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>tcTyVarsOfTyVar</span> <span class='hs-varid'>tyvar</span>
<a name="line-12"></a>	<span class='hs-comment'>-- We do sometimes quantify over skolem TcTyVars</span>
<a name="line-13"></a>
<a name="line-14"></a><a name="tcTyVarsOfTyVar"></a><span class='hs-definition'>tcTyVarsOfTyVar</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcTyVar</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyVarSet</span>
<a name="line-15"></a><span class='hs-definition'>tcTyVarsOfTyVar</span> <span class='hs-varid'>tv</span> <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isCoVar</span> <span class='hs-varid'>tv</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-layout'>(</span><span class='hs-varid'>tyVarKind</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>
<a name="line-16"></a>                   <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>emptyVarSet</span>
<a name="line-17"></a>
<a name="line-18"></a><a name="tcTyVarsOfTypes"></a><span class='hs-definition'>tcTyVarsOfTypes</span> <span class='hs-keyglyph'>::</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyVarSet</span>
<a name="line-19"></a><span class='hs-definition'>tcTyVarsOfTypes</span> <span class='hs-varid'>tys</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>foldr</span> <span class='hs-layout'>(</span><span class='hs-varid'>unionVarSet</span><span class='hs-varop'>.</span><span class='hs-varid'>tcTyVarsOfType</span><span class='hs-layout'>)</span> <span class='hs-varid'>emptyVarSet</span> <span class='hs-varid'>tys</span>
<a name="line-20"></a>
<a name="line-21"></a><a name="tcTyVarsOfPred"></a><span class='hs-definition'>tcTyVarsOfPred</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>PredType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyVarSet</span>
<a name="line-22"></a><span class='hs-definition'>tcTyVarsOfPred</span> <span class='hs-layout'>(</span><span class='hs-conid'>IParam</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>  	<span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty</span>
<a name="line-23"></a><span class='hs-definition'>tcTyVarsOfPred</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span> 	<span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfTypes</span> <span class='hs-varid'>tys</span>
<a name="line-24"></a><span class='hs-definition'>tcTyVarsOfPred</span> <span class='hs-layout'>(</span><span class='hs-conid'>EqPred</span> <span class='hs-varid'>ty1</span> <span class='hs-varid'>ty2</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty1</span> <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>tcTyVarsOfType</span> <span class='hs-varid'>ty2</span>
</pre>\end{code}

Note [Silly type synonym]
~~~~~~~~~~~~~~~~~~~~~~~~~
Consider
	type T a = Int
What are the free tyvars of (T x)?  Empty, of course!  
Here's the example that Ralf Laemmel showed me:
	foo :: (forall a. C u a -> C u a) -> u
	mappend :: Monoid u => u -> u -> u

	bar :: Monoid u => u
	bar = foo (\t -> t `mappend` t)
We have to generalise at the arg to f, and we don't
want to capture the constraint (Monad (C u a)) because
it appears to mention a.  Pretty silly, but it was useful to him.

exactTyVarsOfType is used by the type checker to figure out exactly
which type variables are mentioned in a type.  It's also used in the
smart-app checking code --- see TcExpr.tcIdApp

On the other hand, consider a *top-level* definition
	f = (\x -> x) :: T a -> T a
If we don't abstract over 'a' it'll get fixed to GHC.Prim.Any, and then
if we have an application like (f "x") we get a confusing error message 
involving Any.  So the conclusion is this: when generalising
  - at top level use tyVarsOfType
  - in nested bindings use exactTyVarsOfType
See Trac #1813 for example.

\begin{code}
<pre><a name="line-1"></a><a name="exactTyVarsOfType"></a><span class='hs-definition'>exactTyVarsOfType</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TcType</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyVarSet</span>
<a name="line-2"></a><span class='hs-comment'>-- Find the free type variables (of any kind)</span>
<a name="line-3"></a><span class='hs-comment'>-- but *expand* type synonyms.  See Note [Silly type synonym] above.</span>
<a name="line-4"></a><span class='hs-definition'>exactTyVarsOfType</span> <span class='hs-varid'>ty</span>
<a name="line-5"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty</span>
<a name="line-6"></a>  <span class='hs-keyword'>where</span>
<a name="line-7"></a>    <span class='hs-varid'>go</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>ty'</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>tcView</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty'</span>	<span class='hs-comment'>-- This is the key line</span>
<a name="line-8"></a>    <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-varid'>tv</span><span class='hs-layout'>)</span>         	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>unitVarSet</span> <span class='hs-varid'>tv</span>
<a name="line-9"></a>    <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>     	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>exactTyVarsOfTypes</span> <span class='hs-varid'>tys</span>
<a name="line-10"></a>    <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>	    	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go_pred</span> <span class='hs-varid'>ty</span>
<a name="line-11"></a>    <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>	    	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>arg</span> <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>go</span> <span class='hs-varid'>res</span>
<a name="line-12"></a>    <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-conid'>AppTy</span> <span class='hs-varid'>fun</span> <span class='hs-varid'>arg</span><span class='hs-layout'>)</span>	    	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>fun</span> <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>go</span> <span class='hs-varid'>arg</span>
<a name="line-13"></a>    <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-varid'>tyvar</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>  	  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>delVarSet</span> <span class='hs-layout'>(</span><span class='hs-varid'>go</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span> <span class='hs-varid'>tyvar</span>
<a name="line-14"></a>                                    <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>go_tv</span> <span class='hs-varid'>tyvar</span>
<a name="line-15"></a>
<a name="line-16"></a>    <span class='hs-varid'>go_pred</span> <span class='hs-layout'>(</span><span class='hs-conid'>IParam</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty</span>
<a name="line-17"></a>    <span class='hs-varid'>go_pred</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>exactTyVarsOfTypes</span> <span class='hs-varid'>tys</span>
<a name="line-18"></a>    <span class='hs-varid'>go_pred</span> <span class='hs-layout'>(</span><span class='hs-conid'>EqPred</span> <span class='hs-varid'>ty1</span> <span class='hs-varid'>ty2</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty1</span> <span class='hs-varop'>`unionVarSet`</span> <span class='hs-varid'>go</span> <span class='hs-varid'>ty2</span>
<a name="line-19"></a>
<a name="line-20"></a>    <span class='hs-varid'>go_tv</span> <span class='hs-varid'>tyvar</span> <span class='hs-keyglyph'>|</span> <span class='hs-varid'>isCoVar</span> <span class='hs-varid'>tyvar</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-layout'>(</span><span class='hs-varid'>tyVarKind</span> <span class='hs-varid'>tyvar</span><span class='hs-layout'>)</span>
<a name="line-21"></a>                <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>emptyVarSet</span>
<a name="line-22"></a>
<a name="line-23"></a><a name="exactTyVarsOfTypes"></a><span class='hs-definition'>exactTyVarsOfTypes</span> <span class='hs-keyglyph'>::</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>TcType</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyVarSet</span>
<a name="line-24"></a><span class='hs-definition'>exactTyVarsOfTypes</span> <span class='hs-varid'>tys</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>foldr</span> <span class='hs-layout'>(</span><span class='hs-varid'>unionVarSet</span> <span class='hs-varop'>.</span> <span class='hs-varid'>exactTyVarsOfType</span><span class='hs-layout'>)</span> <span class='hs-varid'>emptyVarSet</span> <span class='hs-varid'>tys</span>
</pre>\end{code}

Find the free tycons and classes of a type.  This is used in the front
end of the compiler.

\begin{code}
<pre><a name="line-1"></a><a name="tyClsNamesOfType"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>NameSet</span>
<a name="line-2"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyVarTy</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span>		    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>emptyNameSet</span>
<a name="line-3"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyConApp</span> <span class='hs-varid'>tycon</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>unitNameSet</span> <span class='hs-layout'>(</span><span class='hs-varid'>getName</span> <span class='hs-varid'>tycon</span><span class='hs-layout'>)</span> <span class='hs-varop'>`unionNameSets`</span> <span class='hs-varid'>tyClsNamesOfTypes</span> <span class='hs-varid'>tys</span>
<a name="line-4"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>IParam</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>ty</span>
<a name="line-5"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>ClassP</span> <span class='hs-varid'>cl</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>unitNameSet</span> <span class='hs-layout'>(</span><span class='hs-varid'>getName</span> <span class='hs-varid'>cl</span><span class='hs-layout'>)</span> <span class='hs-varop'>`unionNameSets`</span> <span class='hs-varid'>tyClsNamesOfTypes</span> <span class='hs-varid'>tys</span>
<a name="line-6"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>PredTy</span> <span class='hs-layout'>(</span><span class='hs-conid'>EqPred</span> <span class='hs-varid'>ty1</span> <span class='hs-varid'>ty2</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>ty1</span> <span class='hs-varop'>`unionNameSets`</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>ty2</span>
<a name="line-7"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>FunTy</span> <span class='hs-varid'>arg</span> <span class='hs-varid'>res</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>arg</span> <span class='hs-varop'>`unionNameSets`</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>res</span>
<a name="line-8"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>AppTy</span> <span class='hs-varid'>fun</span> <span class='hs-varid'>arg</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>fun</span> <span class='hs-varop'>`unionNameSets`</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>arg</span>
<a name="line-9"></a><span class='hs-definition'>tyClsNamesOfType</span> <span class='hs-layout'>(</span><span class='hs-conid'>ForAllTy</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span>	    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>ty</span>
<a name="line-10"></a>
<a name="line-11"></a><a name="tyClsNamesOfTypes"></a><span class='hs-definition'>tyClsNamesOfTypes</span> <span class='hs-keyglyph'>::</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Type</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>NameSet</span>
<a name="line-12"></a><span class='hs-definition'>tyClsNamesOfTypes</span> <span class='hs-varid'>tys</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>foldr</span> <span class='hs-layout'>(</span><span class='hs-varid'>unionNameSets</span> <span class='hs-varop'>.</span> <span class='hs-varid'>tyClsNamesOfType</span><span class='hs-layout'>)</span> <span class='hs-varid'>emptyNameSet</span> <span class='hs-varid'>tys</span>
<a name="line-13"></a>
<a name="line-14"></a><a name="tyClsNamesOfDFunHead"></a><span class='hs-definition'>tyClsNamesOfDFunHead</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>NameSet</span>
<a name="line-15"></a><span class='hs-comment'>-- Find the free type constructors and classes </span>
<a name="line-16"></a><span class='hs-comment'>-- of the head of the dfun instance type</span>
<a name="line-17"></a><span class='hs-comment'>-- The 'dfun_head_type' is because of</span>
<a name="line-18"></a><span class='hs-comment'>--	instance Foo a =&gt; Baz T where ...</span>
<a name="line-19"></a><span class='hs-comment'>-- The decl is an orphan if Baz and T are both not locally defined,</span>
<a name="line-20"></a><span class='hs-comment'>--	even if Foo *is* locally defined</span>
<a name="line-21"></a><span class='hs-definition'>tyClsNamesOfDFunHead</span> <span class='hs-varid'>dfun_ty</span> 
<a name="line-22"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitSigmaTy</span> <span class='hs-varid'>dfun_ty</span> <span class='hs-keyword'>of</span>
<a name="line-23"></a>	<span class='hs-layout'>(</span><span class='hs-keyword'>_</span><span class='hs-layout'>,</span> <span class='hs-keyword'>_</span><span class='hs-layout'>,</span> <span class='hs-varid'>head_ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>tyClsNamesOfType</span> <span class='hs-varid'>head_ty</span>
</pre>\end{code}


%************************************************************************
%*									*
\subsection[TysWiredIn-ext-type]{External types}
%*									*
%************************************************************************

The compiler's foreign function interface supports the passing of a
restricted set of types as arguments and results (the restricting factor
being the )

\begin{code}
<pre><a name="line-1"></a><a name="tcSplitIOType_maybe"></a><span class='hs-definition'>tcSplitIOType_maybe</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyCon</span><span class='hs-layout'>,</span> <span class='hs-conid'>Type</span><span class='hs-layout'>,</span> <span class='hs-conid'>CoercionI</span><span class='hs-layout'>)</span>
<a name="line-2"></a><span class='hs-comment'>-- (isIOType t) returns Just (IO,t',co)</span>
<a name="line-3"></a><span class='hs-comment'>--				if co : t ~ IO t'</span>
<a name="line-4"></a><span class='hs-comment'>--		returns Nothing otherwise</span>
<a name="line-5"></a><span class='hs-definition'>tcSplitIOType_maybe</span> <span class='hs-varid'>ty</span> 
<a name="line-6"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitTyConApp_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-7"></a>	<span class='hs-comment'>-- This split absolutely has to be a tcSplit, because we must</span>
<a name="line-8"></a>	<span class='hs-comment'>-- see the IO type; and it's a newtype which is transparent to splitTyConApp.</span>
<a name="line-9"></a>
<a name="line-10"></a>	<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>io_tycon</span><span class='hs-layout'>,</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>io_res_ty</span><span class='hs-keyglyph'>]</span><span class='hs-layout'>)</span> 
<a name="line-11"></a>	   <span class='hs-keyglyph'>|</span>  <span class='hs-varid'>io_tycon</span> <span class='hs-varop'>`hasKey`</span> <span class='hs-varid'>ioTyConKey</span> 
<a name="line-12"></a>	   <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>io_tycon</span><span class='hs-layout'>,</span> <span class='hs-varid'>io_res_ty</span><span class='hs-layout'>,</span> <span class='hs-conid'>IdCo</span><span class='hs-layout'>)</span>
<a name="line-13"></a>
<a name="line-14"></a>	<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-varid'>tys</span><span class='hs-layout'>)</span>
<a name="line-15"></a>	   <span class='hs-keyglyph'>|</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isRecursiveTyCon</span> <span class='hs-varid'>tc</span><span class='hs-layout'>)</span>
<a name="line-16"></a>	   <span class='hs-layout'>,</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>ty</span><span class='hs-layout'>,</span> <span class='hs-varid'>co1</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>instNewTyCon_maybe</span> <span class='hs-varid'>tc</span> <span class='hs-varid'>tys</span>
<a name="line-17"></a>		  <span class='hs-comment'>-- Newtypes that require a coercion are ok</span>
<a name="line-18"></a>	   <span class='hs-keyglyph'>-&gt;</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tcSplitIOType_maybe</span> <span class='hs-varid'>ty</span> <span class='hs-keyword'>of</span>
<a name="line-19"></a>		<span class='hs-conid'>Nothing</span>		    <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Nothing</span>
<a name="line-20"></a>		<span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty'</span><span class='hs-layout'>,</span> <span class='hs-varid'>co2</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty'</span><span class='hs-layout'>,</span> <span class='hs-varid'>co1</span> <span class='hs-varop'>`mkTransCoI`</span> <span class='hs-varid'>co2</span><span class='hs-layout'>)</span>
<a name="line-21"></a>
<a name="line-22"></a>	<span class='hs-keyword'>_</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Nothing</span>
<a name="line-23"></a>
<a name="line-24"></a><a name="isFFITy"></a><span class='hs-definition'>isFFITy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-25"></a><span class='hs-comment'>-- True for any TyCon that can possibly be an arg or result of an FFI call</span>
<a name="line-26"></a><span class='hs-definition'>isFFITy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-varid'>legalFFITyCon</span> <span class='hs-varid'>ty</span>
<a name="line-27"></a>
<a name="line-28"></a><a name="isFFIArgumentTy"></a><span class='hs-definition'>isFFIArgumentTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Safety</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-29"></a><span class='hs-comment'>-- Checks for valid argument type for a 'foreign import'</span>
<a name="line-30"></a><span class='hs-definition'>isFFIArgumentTy</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>safety</span> <span class='hs-varid'>ty</span> 
<a name="line-31"></a>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-layout'>(</span><span class='hs-varid'>legalOutgoingTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>safety</span><span class='hs-layout'>)</span> <span class='hs-varid'>ty</span>
<a name="line-32"></a>
<a name="line-33"></a><a name="isFFIExternalTy"></a><span class='hs-definition'>isFFIExternalTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-34"></a><span class='hs-comment'>-- Types that are allowed as arguments of a 'foreign export'</span>
<a name="line-35"></a><span class='hs-definition'>isFFIExternalTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-varid'>legalFEArgTyCon</span> <span class='hs-varid'>ty</span>
<a name="line-36"></a>
<a name="line-37"></a><a name="isFFIImportResultTy"></a><span class='hs-definition'>isFFIImportResultTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-38"></a><span class='hs-definition'>isFFIImportResultTy</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>ty</span> 
<a name="line-39"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-layout'>(</span><span class='hs-varid'>legalFIResultTyCon</span> <span class='hs-varid'>dflags</span><span class='hs-layout'>)</span> <span class='hs-varid'>ty</span>
<a name="line-40"></a>
<a name="line-41"></a><a name="isFFIExportResultTy"></a><span class='hs-definition'>isFFIExportResultTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-42"></a><span class='hs-definition'>isFFIExportResultTy</span> <span class='hs-varid'>ty</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-varid'>legalFEResultTyCon</span> <span class='hs-varid'>ty</span>
<a name="line-43"></a>
<a name="line-44"></a><a name="isFFIDynArgumentTy"></a><span class='hs-definition'>isFFIDynArgumentTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-45"></a><span class='hs-comment'>-- The argument type of a foreign import dynamic must be Ptr, FunPtr, Addr,</span>
<a name="line-46"></a><span class='hs-comment'>-- or a newtype of either.</span>
<a name="line-47"></a><span class='hs-definition'>isFFIDynArgumentTy</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyConKey</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>ptrTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>funPtrTyConKey</span><span class='hs-keyglyph'>]</span>
<a name="line-48"></a>
<a name="line-49"></a><a name="isFFIDynResultTy"></a><span class='hs-definition'>isFFIDynResultTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-50"></a><span class='hs-comment'>-- The result type of a foreign export dynamic must be Ptr, FunPtr, Addr,</span>
<a name="line-51"></a><span class='hs-comment'>-- or a newtype of either.</span>
<a name="line-52"></a><span class='hs-definition'>isFFIDynResultTy</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyConKey</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>ptrTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>funPtrTyConKey</span><span class='hs-keyglyph'>]</span>
<a name="line-53"></a>
<a name="line-54"></a><a name="isFFILabelTy"></a><span class='hs-definition'>isFFILabelTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-55"></a><span class='hs-comment'>-- The type of a foreign label must be Ptr, FunPtr, Addr,</span>
<a name="line-56"></a><span class='hs-comment'>-- or a newtype of either.</span>
<a name="line-57"></a><span class='hs-definition'>isFFILabelTy</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyConKey</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>ptrTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>funPtrTyConKey</span><span class='hs-keyglyph'>]</span>
<a name="line-58"></a>
<a name="line-59"></a><a name="isFFIPrimArgumentTy"></a><span class='hs-definition'>isFFIPrimArgumentTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-60"></a><span class='hs-comment'>-- Checks for valid argument type for a 'foreign import prim'</span>
<a name="line-61"></a><span class='hs-comment'>-- Currently they must all be simple unlifted types.</span>
<a name="line-62"></a><span class='hs-definition'>isFFIPrimArgumentTy</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>ty</span>
<a name="line-63"></a>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-layout'>(</span><span class='hs-varid'>legalFIPrimArgTyCon</span> <span class='hs-varid'>dflags</span><span class='hs-layout'>)</span> <span class='hs-varid'>ty</span>
<a name="line-64"></a>
<a name="line-65"></a><a name="isFFIPrimResultTy"></a><span class='hs-definition'>isFFIPrimResultTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-66"></a><span class='hs-comment'>-- Checks for valid result type for a 'foreign import prim'</span>
<a name="line-67"></a><span class='hs-comment'>-- Currently it must be an unlifted type, including unboxed tuples.</span>
<a name="line-68"></a><span class='hs-definition'>isFFIPrimResultTy</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>ty</span>
<a name="line-69"></a>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-layout'>(</span><span class='hs-varid'>legalFIPrimResultTyCon</span> <span class='hs-varid'>dflags</span><span class='hs-layout'>)</span> <span class='hs-varid'>ty</span>
<a name="line-70"></a>
<a name="line-71"></a><a name="isFFIDotnetTy"></a><span class='hs-definition'>isFFIDotnetTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-72"></a><span class='hs-definition'>isFFIDotnetTy</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>ty</span>
<a name="line-73"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>\</span> <span class='hs-varid'>tc</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-layout'>(</span><span class='hs-varid'>legalFIResultTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>||</span> 
<a name="line-74"></a>			   <span class='hs-varid'>isFFIDotnetObjTy</span> <span class='hs-varid'>ty</span> <span class='hs-varop'>||</span> <span class='hs-varid'>isStringTy</span> <span class='hs-varid'>ty</span><span class='hs-layout'>)</span><span class='hs-layout'>)</span> <span class='hs-varid'>ty</span>
<a name="line-75"></a>	<span class='hs-comment'>-- NB: isStringTy used to look through newtypes, but</span>
<a name="line-76"></a>	<span class='hs-comment'>--     it no longer does so.  May need to adjust isFFIDotNetTy</span>
<a name="line-77"></a>	<span class='hs-comment'>--     if we do want to look through newtypes.</span>
<a name="line-78"></a>
<a name="line-79"></a><a name="isFFIDotnetObjTy"></a><span class='hs-definition'>isFFIDotnetObjTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-80"></a><span class='hs-definition'>isFFIDotnetObjTy</span> <span class='hs-varid'>ty</span>
<a name="line-81"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-varid'>check_tc</span> <span class='hs-varid'>t_ty</span>
<a name="line-82"></a>  <span class='hs-keyword'>where</span>
<a name="line-83"></a>   <span class='hs-layout'>(</span><span class='hs-keyword'>_</span><span class='hs-layout'>,</span> <span class='hs-varid'>t_ty</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>tcSplitForAllTys</span> <span class='hs-varid'>ty</span>
<a name="line-84"></a>   <span class='hs-varid'>check_tc</span> <span class='hs-varid'>tc</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getName</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>==</span> <span class='hs-varid'>objectTyConName</span>
<a name="line-85"></a>
<a name="line-86"></a><a name="isFunPtrTy"></a><span class='hs-definition'>isFunPtrTy</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-87"></a><span class='hs-definition'>isFunPtrTy</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyConKey</span> <span class='hs-keyglyph'>[</span><span class='hs-varid'>funPtrTyConKey</span><span class='hs-keyglyph'>]</span>
<a name="line-88"></a>
<a name="line-89"></a><a name="checkRepTyCon"></a><span class='hs-definition'>checkRepTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-layout'>(</span><span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-90"></a><span class='hs-comment'>-- Look through newtypes, but *not* foralls</span>
<a name="line-91"></a><span class='hs-comment'>-- Should work even for recursive newtypes</span>
<a name="line-92"></a><span class='hs-comment'>-- eg Manuel had:	newtype T = MkT (Ptr T)</span>
<a name="line-93"></a><span class='hs-definition'>checkRepTyCon</span> <span class='hs-varid'>check_tc</span> <span class='hs-varid'>ty</span>
<a name="line-94"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>go</span> <span class='hs-conid'>[]</span> <span class='hs-varid'>ty</span>
<a name="line-95"></a>  <span class='hs-keyword'>where</span>
<a name="line-96"></a>    <span class='hs-varid'>go</span> <span class='hs-varid'>rec_nts</span> <span class='hs-varid'>ty</span>
<a name="line-97"></a>      <span class='hs-keyglyph'>|</span> <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>tc</span><span class='hs-layout'>,</span><span class='hs-varid'>tys</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>&lt;-</span> <span class='hs-varid'>splitTyConApp_maybe</span> <span class='hs-varid'>ty</span>
<a name="line-98"></a>      <span class='hs-keyglyph'>=</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>carefullySplitNewType_maybe</span> <span class='hs-varid'>rec_nts</span> <span class='hs-varid'>tc</span> <span class='hs-varid'>tys</span> <span class='hs-keyword'>of</span>
<a name="line-99"></a>      	   <span class='hs-conid'>Just</span> <span class='hs-layout'>(</span><span class='hs-varid'>rec_nts'</span><span class='hs-layout'>,</span> <span class='hs-varid'>ty'</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>go</span> <span class='hs-varid'>rec_nts'</span> <span class='hs-varid'>ty'</span>
<a name="line-100"></a>	   <span class='hs-conid'>Nothing</span>	   	<span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>check_tc</span> <span class='hs-varid'>tc</span>
<a name="line-101"></a>      <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>
<a name="line-102"></a>      <span class='hs-keyglyph'>=</span> <span class='hs-conid'>False</span>
<a name="line-103"></a>
<a name="line-104"></a><a name="checkRepTyConKey"></a><span class='hs-definition'>checkRepTyConKey</span> <span class='hs-keyglyph'>::</span> <span class='hs-keyglyph'>[</span><span class='hs-conid'>Unique</span><span class='hs-keyglyph'>]</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Type</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-105"></a><span class='hs-comment'>-- Like checkRepTyCon, but just looks at the TyCon key</span>
<a name="line-106"></a><span class='hs-definition'>checkRepTyConKey</span> <span class='hs-varid'>keys</span>
<a name="line-107"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>checkRepTyCon</span> <span class='hs-layout'>(</span><span class='hs-keyglyph'>\</span><span class='hs-varid'>tc</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>tyConUnique</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>`elem`</span> <span class='hs-varid'>keys</span><span class='hs-layout'>)</span>
</pre>\end{code}

----------------------------------------------
These chaps do the work; they are not exported
----------------------------------------------

\begin{code}
<pre><a name="line-1"></a><a name="legalFEArgTyCon"></a><span class='hs-definition'>legalFEArgTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-2"></a><span class='hs-definition'>legalFEArgTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-3"></a>  <span class='hs-comment'>-- It's illegal to make foreign exports that take unboxed</span>
<a name="line-4"></a>  <span class='hs-comment'>-- arguments.  The RTS API currently can't invoke such things.  --SDM 7/2000</span>
<a name="line-5"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>boxedMarshalableTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-6"></a>
<a name="line-7"></a><a name="legalFIResultTyCon"></a><span class='hs-definition'>legalFIResultTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-8"></a><span class='hs-definition'>legalFIResultTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span>
<a name="line-9"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>==</span> <span class='hs-varid'>unitTyCon</span>         <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-10"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>	            <span class='hs-keyglyph'>=</span> <span class='hs-varid'>marshalableTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span>
<a name="line-11"></a>
<a name="line-12"></a><a name="legalFEResultTyCon"></a><span class='hs-definition'>legalFEResultTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-13"></a><span class='hs-definition'>legalFEResultTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-14"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>==</span> <span class='hs-varid'>unitTyCon</span>         <span class='hs-keyglyph'>=</span> <span class='hs-conid'>True</span>
<a name="line-15"></a>  <span class='hs-keyglyph'>|</span> <span class='hs-varid'>otherwise</span>               <span class='hs-keyglyph'>=</span> <span class='hs-varid'>boxedMarshalableTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-16"></a>
<a name="line-17"></a><a name="legalOutgoingTyCon"></a><span class='hs-definition'>legalOutgoingTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Safety</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-18"></a><span class='hs-comment'>-- Checks validity of types going from Haskell -&gt; external world</span>
<a name="line-19"></a><span class='hs-definition'>legalOutgoingTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>tc</span>
<a name="line-20"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>marshalableTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span>
<a name="line-21"></a>
<a name="line-22"></a><a name="legalFFITyCon"></a><span class='hs-definition'>legalFFITyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-23"></a><span class='hs-comment'>-- True for any TyCon that can possibly be an arg or result of an FFI call</span>
<a name="line-24"></a><span class='hs-definition'>legalFFITyCon</span> <span class='hs-varid'>tc</span>
<a name="line-25"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>isUnLiftedTyCon</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>||</span> <span class='hs-varid'>boxedMarshalableTyCon</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>||</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>==</span> <span class='hs-varid'>unitTyCon</span>
<a name="line-26"></a>
<a name="line-27"></a><a name="marshalableTyCon"></a><span class='hs-definition'>marshalableTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-28"></a><span class='hs-definition'>marshalableTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span>
<a name="line-29"></a>  <span class='hs-keyglyph'>=</span>  <span class='hs-layout'>(</span><span class='hs-varid'>dopt</span> <span class='hs-conid'>Opt_UnliftedFFITypes</span> <span class='hs-varid'>dflags</span> 
<a name="line-30"></a>      <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isUnLiftedTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-31"></a>      <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isUnboxedTupleTyCon</span> <span class='hs-varid'>tc</span><span class='hs-layout'>)</span>
<a name="line-32"></a>      <span class='hs-varop'>&amp;&amp;</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tyConPrimRep</span> <span class='hs-varid'>tc</span> <span class='hs-keyword'>of</span>	<span class='hs-comment'>-- Note [Marshalling VoidRep]</span>
<a name="line-33"></a>	   <span class='hs-conid'>VoidRep</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-34"></a>	   <span class='hs-keyword'>_</span>       <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span><span class='hs-layout'>)</span>
<a name="line-35"></a>  <span class='hs-varop'>||</span> <span class='hs-varid'>boxedMarshalableTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-36"></a>
<a name="line-37"></a><a name="boxedMarshalableTyCon"></a><span class='hs-definition'>boxedMarshalableTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-38"></a><span class='hs-definition'>boxedMarshalableTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-39"></a>   <span class='hs-keyglyph'>=</span> <span class='hs-varid'>getUnique</span> <span class='hs-varid'>tc</span> <span class='hs-varop'>`elem`</span> <span class='hs-keyglyph'>[</span> <span class='hs-varid'>intTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>int8TyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>int16TyConKey</span>
<a name="line-40"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>int32TyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>int64TyConKey</span>
<a name="line-41"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>wordTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>word8TyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>word16TyConKey</span>
<a name="line-42"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>word32TyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>word64TyConKey</span>
<a name="line-43"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>floatTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>doubleTyConKey</span>
<a name="line-44"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>ptrTyConKey</span><span class='hs-layout'>,</span> <span class='hs-varid'>funPtrTyConKey</span>
<a name="line-45"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>charTyConKey</span>
<a name="line-46"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>stablePtrTyConKey</span>
<a name="line-47"></a>			 <span class='hs-layout'>,</span> <span class='hs-varid'>boolTyConKey</span>
<a name="line-48"></a>			 <span class='hs-keyglyph'>]</span>
<a name="line-49"></a>
<a name="line-50"></a><a name="legalFIPrimArgTyCon"></a><span class='hs-definition'>legalFIPrimArgTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-51"></a><span class='hs-comment'>-- Check args of 'foreign import prim', only allow simple unlifted types.</span>
<a name="line-52"></a><span class='hs-comment'>-- Strictly speaking it is unnecessary to ban unboxed tuples here since</span>
<a name="line-53"></a><span class='hs-comment'>-- currently they're of the wrong kind to use in function args anyway.</span>
<a name="line-54"></a><span class='hs-definition'>legalFIPrimArgTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span>
<a name="line-55"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>dopt</span> <span class='hs-conid'>Opt_UnliftedFFITypes</span> <span class='hs-varid'>dflags</span>
<a name="line-56"></a>    <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isUnLiftedTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-57"></a>    <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>not</span> <span class='hs-layout'>(</span><span class='hs-varid'>isUnboxedTupleTyCon</span> <span class='hs-varid'>tc</span><span class='hs-layout'>)</span>
<a name="line-58"></a>
<a name="line-59"></a><a name="legalFIPrimResultTyCon"></a><span class='hs-definition'>legalFIPrimResultTyCon</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>DynFlags</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>TyCon</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Bool</span>
<a name="line-60"></a><span class='hs-comment'>-- Check result type of 'foreign import prim'. Allow simple unlifted</span>
<a name="line-61"></a><span class='hs-comment'>-- types and also unboxed tuple result types '... -&gt; (# , , #)'</span>
<a name="line-62"></a><span class='hs-definition'>legalFIPrimResultTyCon</span> <span class='hs-varid'>dflags</span> <span class='hs-varid'>tc</span>
<a name="line-63"></a>  <span class='hs-keyglyph'>=</span> <span class='hs-varid'>dopt</span> <span class='hs-conid'>Opt_UnliftedFFITypes</span> <span class='hs-varid'>dflags</span>
<a name="line-64"></a>    <span class='hs-varop'>&amp;&amp;</span> <span class='hs-varid'>isUnLiftedTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-65"></a>    <span class='hs-varop'>&amp;&amp;</span> <span class='hs-layout'>(</span><span class='hs-varid'>isUnboxedTupleTyCon</span> <span class='hs-varid'>tc</span>
<a name="line-66"></a>        <span class='hs-varop'>||</span> <span class='hs-keyword'>case</span> <span class='hs-varid'>tyConPrimRep</span> <span class='hs-varid'>tc</span> <span class='hs-keyword'>of</span>	<span class='hs-comment'>-- Note [Marshalling VoidRep]</span>
<a name="line-67"></a>	   <span class='hs-conid'>VoidRep</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>False</span>
<a name="line-68"></a>	   <span class='hs-keyword'>_</span>       <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>True</span><span class='hs-layout'>)</span>
</pre>\end{code}

Note [Marshalling VoidRep]
~~~~~~~~~~~~~~~~~~~~~~~~~~
We don't treat State# (whose PrimRep is VoidRep) as marshalable.
In turn that means you can't write
	foreign import foo :: Int -> State# RealWorld

Reason: the back end falls over with panic "primRepHint:VoidRep";
	and there is no compelling reason to permit it
</body>
</html>