@@ -22,7 +22,8 @@ module Language.PureScript.TypeChecker.Types (
22import Data.List
22import Data.List
23import Data.Maybe (isNothing, isJust, fromMaybe)
23import Data.Maybe (isNothing, isJust, fromMaybe)
24import qualified Data.Data as D
24import qualified Data.Data as D
25−import Data.Generics (everything, mkT, something, everywhere, mkQ)
26+ (mkM, everywhereM, everything, mkT, something, everywhere, mkQ)
27import Language.PureScript.Values
28import Language.PureScript.Values
28import Language.PureScript.Types
29import Language.PureScript.Types
@@ -169,8 +170,10 @@ typesOf moduleName vals = do
169 escapeCheck val ty
170 escapeCheck val ty
170 return triple
171 return triple
171 forM_ tys $ skolemEscapeCheck . snd . snd
172 forM_ tys $ skolemEscapeCheck . snd . snd
173+ forM tys $ \(ident, (val, ty)) -> do
174+ val' <- replaceTypeClassDictionaries val
172− return $ map (\(ident, (val, ty)) -> ( ident, ( overTypes (desaturateAllTypeSynonyms . setifyAll) val
175+ return (ident, (overTypes (desaturateAllTypeSynonyms . setifyAll) $ val'
173− , varIfUnknown . desaturateAllTypeSynonyms . setifyAll $ ty))) tys
176+ , varIfUnknown . desaturateAllTypeSynonyms . setifyAll $ ty))
175isTyped :: (Ident, Value) -> (Ident, (Value, Maybe Type))
178isTyped :: (Ident, Value) -> (Ident, (Value, Maybe Type))
176isTyped (name, TypedValue value ty) = (name, (value, Just ty))
179isTyped (name, TypedValue value ty) = (name, (value, Just ty))
@@ -179,6 +182,15 @@ isTyped (name, value) = (name, (value, Nothing))
179overTypes :: (Type -> Type) -> Value -> Value
182overTypes :: (Type -> Type) -> Value -> Value
180overTypes f = everywhere (mkT f)
183overTypes f = everywhere (mkT f)
185+replaceTypeClassDictionaries :: Value -> Check Value
186+replaceTypeClassDictionaries = everywhereM (mkM go)
188+ go (TypeClassDictionary constraint dicts) = entails dicts constraint
189+ go other = return other
191+entails :: [(Ident, Qualified ProperName, Type)] -> (Qualified ProperName, Type) -> Check Value
192+entails _ _ = return $ Var $ Qualified Nothing $ Ident "placeholder" -- TODO
182escapeCheck :: Value -> Type -> Subst ()
194escapeCheck :: Value -> Type -> Subst ()
183escapeCheck value ty = do
195escapeCheck value ty = do
184 subst <- substSubst <$> getSubstState
196 subst <- substSubst <$> getSubstState
@@ -319,7 +331,9 @@ infer' (Var var) = do
319 ty <- lookupVariable moduleName var
331 ty <- lookupVariable moduleName var
320 ty' <- replaceAllTypeSynonyms ty
332 ty' <- replaceAllTypeSynonyms ty
321 case ty' of
333 case ty' of
334+ ConstrainedType constraints _ -> do
335+ dicts <- getTypeClassDictionaries
322− ConstrainedType constraints _ -> return $ TypedValue (App (Var var) [TypeClassDictionary constraints]) ty'
336+ return $ TypedValue (App (Var var) (map (flip TypeClassDictionary dicts) constraints)) ty'
323 _ -> return $ TypedValue (Var var) ty'
337 _ -> return $ TypedValue (Var var) ty'
324infer' (Block ss) = do
338infer' (Block ss) = do
325 ret <- fresh
339 ret <- fresh
@@ -597,8 +611,9 @@ check' val (ForAll idents ty) = do
597 sk <- skolemize idents ty
611 sk <- skolemize idents ty
598 check val sk
612 check val sk
599check' val (ConstrainedType constraints ty) = do
613check' val (ConstrainedType constraints ty) = do
600− val' <- check val ty
614+ let dictName = Ident "__dict" -- TODO
615+ val' <- withTypeClassDictionaries (map (\(className, instanceTy) -> (dictName, className, instanceTy)) constraints) $ check val ty
601− return $ Abs (map (\_ -> Ident "__dict") constraints) val'
616+ return $ Abs (map (\_ -> dictName) constraints) val'
602check' val u@(TUnknown _) = do
617check' val u@(TUnknown _) = do
603 val'@(TypedValue _ ty) <- infer val
618 val'@(TypedValue _ ty) <- infer val
604 -- Don't unify an unknown with an inferred polytype
619 -- Don't unify an unknown with an inferred polytype
@@ -737,7 +752,8 @@ checkFunctionApplication' fn (SaturatedTypeSynonym name tyArgs) args ret = do
737 ty <- expandTypeSynonym name tyArgs
752 ty <- expandTypeSynonym name tyArgs
738 checkFunctionApplication fn ty args ret
753 checkFunctionApplication fn ty args ret
739checkFunctionApplication' fn (ConstrainedType constraints fnTy) args ret = do
754checkFunctionApplication' fn (ConstrainedType constraints fnTy) args ret = do
755+ dicts <- getTypeClassDictionaries
740− checkFunctionApplication' (App fn [TypeClassDictionary constraints]) fnTy args ret
756+ checkFunctionApplication' (App fn (map (flip TypeClassDictionary dicts) constraints)) fnTy args ret
741checkFunctionApplication' _ fnTy args ret = throwError $ "Applying a function of type "
757checkFunctionApplication' _ fnTy args ret = throwError $ "Applying a function of type "
742 ++ prettyPrintType fnTy
758 ++ prettyPrintType fnTy
743 ++ " to argument(s) " ++ intercalate ", " (map prettyPrintValue args)
759 ++ " to argument(s) " ++ intercalate ", " (map prettyPrintValue args)