1{-# OPTIONS_GHC -Wall #-}
2module Canonicalize.Pattern
12import qualified Data.Map.Strict as Map
14import qualified AST.Canonical as Can
15import qualified AST.Source as Src
16import qualified Canonicalize.Environment as Env
17import qualified Canonicalize.Environment.Dups as Dups
18import qualified Canonicalize.Result as Result
19import qualified Data.Index as Index
20import qualified Elm.Name as N
21import qualified Reporting.Annotation as A
22import qualified Reporting.Error.Canonicalize as Error
23import qualified Reporting.Region as R
31 Result.Result i w Error.Error a
35 Map.Map N.Name (A.Located Can.Destructor)
42verify :: Error.DuplicatePatternContext -> Result DupsDict w a -> Result i w (a, Bindings)
43verify context (Result.Result k) =
44 Result.Result $ \info warnings bad good ->
46 (\_ warnings1 errors ->
47 bad info warnings1 errors
49 (\bindings warnings1 value ->
50 case Dups.detect (Error.DuplicatePattern context) bindings of
53 (\() () errs -> bad info warnings1 errs)
54 (\() () dict -> good info warnings1 (value, dict))
63 Dups.Dict () (A.Located Can.Destructor)
66canonicalizeArg :: Env.Env -> Index.ZeroBased -> Src.Pattern -> Result DupsDict w Can.Arg
67canonicalizeArg env index pattern =
68 Can.Arg index <$> canonicalize env index pattern
71canonicalize :: Env.Env -> Index.ZeroBased -> Src.Pattern -> Result DupsDict w Can.Pattern
72canonicalize env index pattern =
73 process env (Can.DRoot index) pattern
80process :: Env.Env -> Can.Destructor -> Src.Pattern -> Result DupsDict w Can.Pattern
81process env destructor (A.At region pattern) =
85 Result.ok Can.PAnything
88 logVar name region destructor (Can.PVar name)
91 logFields fields destructor (Can.PRecord (map A.drop fields))
98 <$> process env (Can.DIndex Index.first destructor) a
99 <*> process env (Can.DIndex Index.second destructor) b
100 <*> processTuple region env destructor cs
102 Src.PCtor nameRegion maybePrefix name patterns ->
104 toCanonicalArg index ptrn tipe =
105 Can.PatternCtorArg index tipe
106 <$> process env (Can.DIndex index destructor) ptrn
108 do (Env.Pattern home tipe vars alts args) <- Env.findPattern nameRegion env maybePrefix name
109 verifiedList <- Index.indexedZipWithA toCanonicalArg patterns args
111 Index.LengthMatch cargs ->
112 Result.ok (Can.PCtor home tipe vars alts name cargs)
114 Index.LengthMismatch actualLength expectedLength ->
115 Result.throw (error "TODO" region actualLength expectedLength)
117 Src.PList patterns ->
118 Can.PList <$> processList env destructor patterns
120 Src.PCons first rest ->
122 <$> process env (Can.DIndex Index.first destructor) first
123 <*> process env (Can.DIndex Index.second destructor) rest
125 Src.PAlias ptrn (A.At reg name) ->
126 do cpattern <- process env destructor ptrn
127 logVar name reg destructor (Can.PAlias cpattern name)
130 Result.ok (Can.PChr chr)
133 Result.ok (Can.PStr str)
136 Result.ok (Can.PInt int)
139processTuple :: R.Region -> Env.Env -> Can.Destructor -> [Src.Pattern] -> Result DupsDict w (Maybe Can.Pattern)
140processTuple tupleRegion env destructor extras =
146 Just <$> process env (Can.DIndex Index.third destructor) three
149 let (A.At r1 _, A.At r2 _) = (head others, last others) in
150 Result.throw (Error.TupleLargerThanThree tupleRegion (R.merge r1 r2))
153processList :: Env.Env -> Can.Destructor -> [Src.Pattern] -> Result DupsDict w [Can.Pattern]
154processList env destructor list =
159 pattern : otherPatterns ->
161 <$> process env (Can.DIndex Index.first destructor) pattern
162 <*> processList env (Can.DIndex Index.second destructor) otherPatterns
169logVar :: N.Name -> R.Region -> Can.Destructor -> a -> Result DupsDict w a
170logVar name region destructor value =
171 Result.Result $ \bindings warnings _ ok ->
173 (Dups.insert name region () (A.At region destructor) bindings)
178logFields :: [A.Located N.Name] -> Can.Destructor -> a -> Result DupsDict w a
179logFields fields destructor value =
181 addField (A.At region name) dict =
182 Dups.insert name region () (A.At region (Can.DField name destructor)) dict
184 Result.Result $ \bindings warnings _ ok ->
185 ok (foldr addField bindings fields) warnings value
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list