@@ -3,6 +3,7 @@ module Type.Unify (unify) where
33import Type.Type
44import qualified Data.UnionFind.IO as UF
55import qualified Data.Map as Map
6+import qualified Data.Maybe as Maybe
67import qualified Type.State as TS
78import Control.Arrow (first,second)
89import Control.Monad.State
@@ -78,25 +79,26 @@ actuallyUnify span variable1 variable2 = do
7879
7980 unifyNumber svar name
8081 | name `elem` ["Int","Float","number"] = flexAndUnify svar
81− | otherwise = TS.addError span "Expecting a number (Int or Float)" variable1 variable2
82+ | otherwise = TS.addError span (Just hint) variable1 variable2
83+ where hint = "A number must be an Int or Float"
8284
83− comparableError str = TS.addError span (str ++ msg) variable1 variable2
84− where msg = "Expecting something comparable such as an\n" ++
85− "Int, Float, Char, String, or a list or tuple of comparables."
85+ comparableError maybe =
86+ TS.addError span (Just $ Maybe.fromMaybe msg maybe) variable1 variable2
87+ where msg = "A comparable must be an Int, Float, Char, String, list, or tuple"
8688
8789 unifyComparable var name
8890 | name `elem` ["Int","Float","Char","String","comparable"] = flexAndUnify var
89− | otherwise = comparableError ""
91+ | otherwise = comparableError Nothing
9092
9193 unifyComparableStructure varSuper varFlex =
9294 do struct <- liftIO $ collectApps varFlex
9395 case struct of
94− Other -> comparableError ""
96+ Other -> comparableError Nothing
9597 List v -> do flexAndUnify varSuper
9698 unify' v =<< liftIO (var $ Is Comparable)
9799 Tuple vs
98100 | length vs > 6 ->
99− comparableError "Cannot compare a tuple with more than 6 elements.\n"
101+ comparableError $ Just "Cannot compare a tuple with more than 6 elements"
100102 | otherwise ->
101103 do flexAndUnify varSuper
102104 cmpVars <- liftIO $ forM [1..length vs] $ \_ -> var (Is Comparable)
@@ -106,13 +108,12 @@ actuallyUnify span variable1 variable2 = do
106108 do struct <- liftIO $ collectApps varFlex
107109 case struct of
108110 List _ -> flexAndUnify varSuper
109− _ -> comparableError ""
111+ _ -> comparableError Nothing
110112
111− rigidError variable = TS.addError span msg variable1 variable2
112− where
113− msg = concat
114− [ "Cannot unify rigid type variable '", render (pretty Never variable), "'.\n"
115− , "It is likely that a type annotation is not general enough." ]
113+ rigidError variable = TS.addError span (Just hint) variable1 variable2
114+ where hint = "There is a problem with the '" ++
115+ render (pretty Never variable) ++
116+ "' in the type signature. It currently is not possible to unify type variables that appear in top-level declarations and again in subexpressions"
116117
117118 superUnify =
118119 case (flex desc1, flex desc2, name desc1, name desc2) of
@@ -138,7 +139,7 @@ actuallyUnify span variable1 variable2 = do
138139
139140 (Rigid, _, _, _) -> rigidError variable1
140141 (_, Rigid, _, _) -> rigidError variable2
141− _ -> TS.addError span "" variable1 variable2
142+ _ -> TS.addError span Nothing variable1 variable2
142143
143144 case (structure desc1, structure desc2) of
144145 (Nothing, Nothing) | flex desc1 == Flexible && flex desc1 == Flexible -> merge
@@ -193,5 +194,5 @@ actuallyUnify span variable1 variable2 = do
193194 eat (x:xs) (y:ys) = eat xs ys
194195 eat xs ys = xs
195196
196− _ -> TS.addError span "" variable1 variable2
197+ _ -> TS.addError span Nothing variable1 variable2
197198