+tc_inst_decl2 dfun_id inst_binds
+ = do { let rigid_info = InstSkol
+ inst_ty = idType dfun_id
+ loc = getSrcSpan dfun_id
+
+ -- Instantiate the instance decl with skolem constants
+ ; (inst_tyvars', dfun_theta', inst_head') <- tcSkolSigType rigid_info inst_ty
+ -- These inst_tyvars' scope over the 'where' part
+ -- Those tyvars are inside the dfun_id's type, which is a bit
+ -- bizarre, but OK so long as you realise it!
+ ; let
+ (clas, inst_tys') = tcSplitDFunHead inst_head'
+ (class_tyvars, sc_theta, sc_sels, op_items) = classBigSig clas
+
+ -- Instantiate the super-class context with inst_tys
+ sc_theta' = substTheta (zipOpenTvSubst class_tyvars inst_tys') sc_theta
+
+ -- Create dictionary Ids from the specified instance contexts.
+ ; dfun_ev_vars <- newEvVars dfun_theta'
+ ; self_dict <- newSelfDict clas inst_tys'
+ -- Default-method Ids may be mentioned in synthesised RHSs,
+ -- but they'll already be in the environment.
+
+ -- Cook up a binding for "self = df d1 .. dn",
+ -- to use in each method binding
+ -- Why? See Note [Subtle interaction of recursion and overlap]
+ ; let self_ev_bind = EvBind self_dict $
+ EvDFunApp dfun_id (mkTyVarTys inst_tyvars') dfun_ev_vars
+
+ -- Deal with 'SPECIALISE instance' pragmas
+ -- See Note [SPECIALISE instance pragmas]
+ ; spec_info <- tcSpecInstPrags dfun_id inst_binds
+
+ -- Typecheck the methods
+ ; (meth_ids, meth_binds)
+ <- tcExtendTyVarEnv inst_tyvars' $
+ tcInstanceMethods dfun_id clas inst_tyvars' dfun_ev_vars
+ inst_tys' self_ev_bind spec_info
+ op_items inst_binds
+
+ -- Figure out bindings for the superclass context
+ ; let tc_sc = tcSuperClass inst_tyvars' dfun_ev_vars self_ev_bind
+ (sc_eqs, sc_dicts) = splitAt (classSCNEqs clas) sc_theta'
+ ; (sc_dict_ids, sc_binds) <- ASSERT( equalLength sc_sels sc_dicts )
+ ASSERT( all isEqPred sc_eqs )
+ mapAndUnzipM tc_sc (sc_sels `zip` sc_dicts)
+
+ -- NOT FINISHED!
+ ; (_eq_sc_binds, sc_eq_vars) <- checkConstraints InstSkol emptyVarSet
+ inst_tyvars' dfun_ev_vars $
+ emitWanteds ScOrigin sc_eqs
+
+ -- Create the result bindings
+ ; let dict_constr = classDataCon clas
+ dict_bind = mkVarBind self_dict dict_rhs
+ dict_rhs = foldl mk_app inst_constr dict_and_meth_ids
+ dict_and_meth_ids = sc_dict_ids ++ meth_ids
+ inst_constr = L loc $ wrapId (mkWpEvVarApps sc_eq_vars
+ <.> mkWpTyApps inst_tys')
+ (dataConWrapId dict_constr)
+ -- We don't produce a binding for the dict_constr; instead we
+ -- rely on the simplifier to unfold this saturated application
+ -- We do this rather than generate an HsCon directly, because
+ -- it means that the special cases (e.g. dictionary with only one
+ -- member) are dealt with by the common MkId.mkDataConWrapId code rather
+ -- than needing to be repeated here.
+
+ mk_app :: LHsExpr Id -> Id -> LHsExpr Id
+ mk_app fun arg_id = L loc (HsApp fun (L loc (wrapId arg_wrapper arg_id)))
+ arg_wrapper = mkWpEvVarApps dfun_ev_vars <.> mkWpTyApps (mkTyVarTys inst_tyvars')
+
+ -- Do not inline the dfun; instead give it a magic DFunFunfolding
+ -- See Note [ClassOp/DFun selection]
+ -- See also note [Single-method classes]
+ dfun_id_w_fun = dfun_id
+ `setIdUnfolding` mkDFunUnfolding inst_ty (map Var dict_and_meth_ids)
+ -- Not right for equality superclasses
+ `setInlinePragma` dfunInlinePragma
+
+ (spec_inst_prags, _) = spec_info
+ main_bind = AbsBinds { abs_tvs = inst_tyvars'
+ , abs_ev_vars = dfun_ev_vars
+ , abs_exports = [(inst_tyvars', dfun_id_w_fun, self_dict,
+ SpecPrags spec_inst_prags)]
+ , abs_ev_binds = emptyTcEvBinds
+ , abs_binds = unitBag dict_bind }
+
+ ; return (unitBag (L loc main_bind) `unionBags`
+ listToBag meth_binds `unionBags`
+ listToBag sc_binds)
+ }
+
+------------------------------
+tcSpecInstPrags :: DFunId -> InstBindings Name
+ -> TcM ([Located TcSpecPrag], PragFun)
+tcSpecInstPrags _ (NewTypeDerived {})
+ = return ([], \_ -> [])
+tcSpecInstPrags dfun_id (VanillaInst binds uprags _)
+ = do { spec_inst_prags <- mapM (wrapLocM (tcSpecInst dfun_id)) $
+ filter isSpecInstLSig uprags
+ -- The filter removes the pragmas for methods
+ ; return (spec_inst_prags, mkPragFun uprags binds) }
+
+------------------------------
+tcSuperClass :: [TyVar] -> [EvVar]
+ -> EvBind
+ -> (Id, PredType) -> TcM (Id, LHsBind Id)
+-- Build a top level decl like
+-- sc_op = /\a \d. let this = ... in
+-- let sc = ... in
+-- sc
+-- The "this" part is just-in-case (discarded if not used)
+-- See Note [Recursive superclasses]
+tcSuperClass tyvars dicts
+ self_ev_bind@(EvBind self_dict _)
+ (sc_sel, sc_pred)
+ = do { (ev_binds, wanted, sc_dict)
+ <- newImplication InstSkol emptyVarSet tyvars dicts $
+ emitWanted ScOrigin sc_pred
+
+ ; simplifySuperClass self_dict wanted
+ -- We include self_dict in the 'givens'; the simplifier
+ -- is clever enough to stop sc_pred geting bound by just
+ -- selecting from self_dict!!
+
+ ; uniq <- newUnique
+ ; let sc_op_ty = mkForAllTys tyvars $ mkPiTypes dicts (varType sc_dict)
+ sc_op_name = mkDerivedInternalName mkClassOpAuxOcc uniq
+ (getName sc_sel)
+ sc_op_id = mkLocalId sc_op_name sc_op_ty
+ sc_op_bind = VarBind { var_id = sc_op_id, var_inline = False
+ , var_rhs = L noSrcSpan $ wrapId sc_wrapper sc_dict }
+ sc_wrapper = mkWpTyLams tyvars
+ <.> mkWpLams dicts
+ <.> mkWpLet (EvBinds (unitBag self_ev_bind))
+ <.> mkWpLet ev_binds
+
+ ; return (sc_op_id, noLoc sc_op_bind) }
+\end{code}
+
+Note [Recursive superclasses]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+See Trac #1470 for why we would *like* to add "self_dict" to the
+available instances here. But we can't do so because then the superclases
+get satisfied by selection from self_dict, and that leads to an immediate
+loop. What we need is to add self_dict to Avails without adding its
+superclasses, and we currently have no way to do that.
+
+Note [SPECIALISE instance pragmas]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+Consider
+
+ instance (Ix a, Ix b) => Ix (a,b) where
+ {-# SPECIALISE instance Ix (Int,Int) #-}
+ range (x,y) = ...
+
+We do *not* want to make a specialised version of the dictionary
+function. Rather, we want specialised versions of each method.
+Thus we should generate something like this:
+
+ $dfIx :: (Ix a, Ix x) => Ix (a,b)
+ {- DFUN [$crange, ...] -}
+ $dfIx da db = Ix ($crange da db) (...other methods...)
+
+ $dfIxPair :: (Ix a, Ix x) => Ix (a,b)
+ {- DFUN [$crangePair, ...] -}
+ $dfIxPair = Ix ($crangePair da db) (...other methods...)
+
+ $crange :: (Ix a, Ix b) -> ((a,b),(a,b)) -> [(a,b)]
+ {-# SPECIALISE $crange :: ((Int,Int),(Int,Int)) -> [(Int,Int)] #-}
+ $crange da db = <blah>
+
+ {-# RULE range ($dfIx da db) = $crange da db #-}
+
+Note that
+
+ * The RULE is unaffected by the specialisation. We don't want to
+ specialise $dfIx, because then it would need a specialised RULE
+ which is a pain. The single RULE works fine at all specialisations.
+ See Note [How instance declarations are translated] above
+
+ * Instead, we want to specialise the *method*, $crange
+
+In practice, rather than faking up a SPECIALISE pragama for each
+method (which is painful, since we'd have to figure out its
+specialised type), we call tcSpecPrag *as if* were going to specialise
+$dfIx -- you can see that in the call to tcSpecInst. That generates a
+SpecPrag which, as it turns out, can be used unchanged for each method.
+The "it turns out" bit is delicate, but it works fine!
+
+\begin{code}
+tcSpecInst :: Id -> Sig Name -> TcM TcSpecPrag
+tcSpecInst dfun_id prag@(SpecInstSig hs_ty)
+ = addErrCtxt (spec_ctxt prag) $
+ do { let name = idName dfun_id
+ ; (tyvars, theta, tau) <- tcHsInstHead hs_ty
+ ; let spec_ty = mkSigmaTy tyvars theta tau
+ ; co_fn <- tcSubType (SpecPragOrigin name) (SigSkol SpecInstCtxt)
+ (idType dfun_id) spec_ty
+ ; return (SpecPrag co_fn defaultInlinePragma) }
+ where
+ spec_ctxt prag = hang (ptext (sLit "In the SPECIALISE pragma")) 2 (ppr prag)
+
+tcSpecInst _ _ = panic "tcSpecInst"
+\end{code}
+
+%************************************************************************
+%* *
+ Type-checking an instance method
+%* *
+%************************************************************************
+
+tcInstanceMethod
+- Make the method bindings, as a [(NonRec, HsBinds)], one per method
+- Remembering to use fresh Name (the instance method Name) as the binder
+- Bring the instance method Ids into scope, for the benefit of tcInstSig
+- Use sig_fn mapping instance method Name -> instance tyvars
+- Ditto prag_fn
+- Use tcValBinds to do the checking