[project @ 1998-12-02 13:17:09 by simonm]
[ghc-hetmet.git] / ghc / compiler / typecheck / TcPat.lhs
1 %
2 % (c) The GRASP/AQUA Project, Glasgow University, 1992-1998
3 %
4 \section[TcPat]{Typechecking patterns}
5
6 \begin{code}
7 module TcPat ( tcPat, tcVarPat, badFieldCon ) where
8
9 #include "HsVersions.h"
10
11 import HsSyn            ( InPat(..), OutPat(..), HsLit(..), HsExpr(..), Sig(..) )
12 import RnHsSyn          ( RenamedPat )
13 import TcHsSyn          ( TcPat, TcIdBndr )
14
15 import TcMonad
16 import Inst             ( Inst, OverloadedLit(..), InstOrigin(..),
17                           emptyLIE, plusLIE, LIE,
18                           newMethod, newMethodWithGivenTy, newOverloadedLit, 
19                           newDicts, instToIdBndr
20                         )
21 import Name             ( Name, getOccName, getSrcLoc )
22 import FieldLabel       ( fieldLabelName )
23 import TcEnv            ( TcIdOcc(..), tcLookupGlobalValue, 
24                           tcLookupGlobalValueByKey, newLocalId, badCon
25                         )
26 import TcType           ( TcType, TcTyVar, tcInstTyVars )
27 import TcUnify          ( unifyTauTy, unifyListTy,
28                           unifyTupleTy, unifyUnboxedTupleTy
29                         )
30
31 import Bag              ( Bag )
32 import CmdLineOpts      ( opt_IrrefutableTuples )
33 import DataCon          ( DataCon, dataConSig, dataConFieldLabels, dataConSourceArity )
34 import Id               ( Id, idType, isDataConId_maybe )
35 import Type             ( Type, substFlexiTy, substFlexiTheta, mkTyConApp )
36 import TysPrim          ( charPrimTy, intPrimTy, floatPrimTy,
37                           doublePrimTy, addrPrimTy
38                         )
39 import TysWiredIn       ( charTy, stringTy, intTy )
40 import SrcLoc           ( SrcLoc )
41 import Unique           ( eqClassOpKey, geClassOpKey, minusClassOpKey )
42 import Bag
43 import Util             ( zipEqual )
44 import Outputable
45 \end{code}
46
47
48 %************************************************************************
49 %*                                                                      *
50 \subsection{Variable patterns}
51 %*                                                                      *
52 %************************************************************************
53
54 \begin{code}
55 tcVarPat :: (Name -> Maybe (TcIdBndr s))        -- Info about signatures
56          -> Name
57          -> TcType s                    -- Expected type
58          -> TcM s (TcIdBndr s)          -- The monomorphic Id; this is put in the pattern itself
59
60 tcVarPat sig_fn binder_name pat_ty
61  = case sig_fn binder_name of
62         Nothing -> newLocalId (getOccName binder_name) pat_ty           `thenNF_Tc` \ bndr_id ->
63                    returnTc bndr_id
64
65         Just bndr_id -> tcAddSrcLoc (getSrcLoc binder_name)             $
66                         unifyTauTy pat_ty (idType bndr_id)              `thenTc_`
67                         returnTc bndr_id
68 \end{code}
69
70
71 %************************************************************************
72 %*                                                                      *
73 \subsection{Typechecking patterns}
74 %*                                                                      *
75 %************************************************************************
76
77 \begin{code}
78 tcPat :: (Name -> Maybe (TcIdBndr s))   -- Info about signatures
79       -> RenamedPat
80       -> TcType s                       -- Expected type
81       -> TcM s (TcPat s, 
82                 LIE s,                  -- Required by n+k and literal pats
83                 Bag (TcTyVar s),        -- TyVars bound by the pattern
84                 Bag (Name, TcIdBndr s), -- Ids bound by the pattern, along with the Name under
85                                         --      which it occurs in the pattern
86                                         --      The two aren't the same because we conjure up a new
87                                         --      local name for each variable.
88                 LIE s)                  -- Dicts or methods [see below] bound by the pattern
89 \end{code}
90
91
92 %************************************************************************
93 %*                                                                      *
94 \subsection{Variables, wildcards, lazy pats, as-pats}
95 %*                                                                      *
96 %************************************************************************
97
98 \begin{code}
99 tcPat sig_fn (VarPatIn name) pat_ty
100   = tcVarPat sig_fn name pat_ty         `thenTc` \ bndr_id ->
101     returnTc (VarPat (TcId bndr_id), emptyLIE, emptyBag, unitBag (name, bndr_id), emptyLIE)
102
103 tcPat sig_fn (LazyPatIn pat) pat_ty
104   = tcPat sig_fn pat pat_ty             `thenTc` \ (pat', lie_req, tvs, ids, lie_avail) ->
105     returnTc (LazyPat pat', lie_req, tvs, ids, lie_avail)
106
107 tcPat sig_fn pat_in@(AsPatIn name pat) pat_ty
108   = tcVarPat sig_fn name pat_ty         `thenTc` \ bndr_id ->
109     tcPat sig_fn pat pat_ty             `thenTc` \ (pat', lie_req, tvs, ids, lie_avail) ->
110     tcAddErrCtxt (patCtxt pat_in)       $
111     returnTc (AsPat (TcId bndr_id) pat', lie_req, 
112               tvs, (name, bndr_id) `consBag` ids, 
113               lie_avail)
114
115 tcPat sig_fn WildPatIn pat_ty
116   = returnTc (WildPat pat_ty, emptyLIE, emptyBag, emptyBag, emptyLIE)
117
118 tcPat sig_fn (NegPatIn pat) pat_ty
119   = tcPat sig_fn (negate_lit pat) pat_ty
120   where
121     negate_lit (LitPatIn (HsInt  i)) = LitPatIn (HsInt  (-i))
122     negate_lit (LitPatIn (HsFrac f)) = LitPatIn (HsFrac (-f))
123     negate_lit _                     = panic "TcPat:negate_pat"
124
125 tcPat sig_fn (ParPatIn parend_pat) pat_ty
126   = tcPat sig_fn parend_pat pat_ty
127 \end{code}
128
129 %************************************************************************
130 %*                                                                      *
131 \subsection{Explicit lists and tuples}
132 %*                                                                      *
133 %************************************************************************
134
135 \begin{code}
136 tcPat sig_fn pat_in@(ListPatIn pats) pat_ty
137   = tcAddErrCtxt (patCtxt pat_in)               $
138     unifyListTy pat_ty                          `thenTc` \ elem_ty ->
139     tcPats sig_fn pats (repeat elem_ty)         `thenTc` \ (pats', lie_req, tvs, ids, lie_avail) ->
140     returnTc (ListPat elem_ty pats', lie_req, tvs, ids, lie_avail)
141
142 tcPat sig_fn pat_in@(TuplePatIn pats boxed) pat_ty
143   = tcAddErrCtxt (patCtxt pat_in)       $
144
145     (if boxed
146      then unifyTupleTy        arity pat_ty
147      else unifyUnboxedTupleTy arity pat_ty)     `thenTc` \ arg_tys ->
148
149     tcPats sig_fn pats arg_tys                  `thenTc` \ (pats', lie_req, tvs, ids, lie_avail) ->
150
151         -- possibly do the "make all tuple-pats irrefutable" test:
152     let
153         unmangled_result = TuplePat pats' boxed
154
155         -- Under flag control turn a pattern (x,y,z) into ~(x,y,z)
156         -- so that we can experiment with lazy tuple-matching.
157         -- This is a pretty odd place to make the switch, but
158         -- it was easy to do.
159
160         possibly_mangled_result
161           | opt_IrrefutableTuples && boxed = LazyPat unmangled_result
162           | otherwise                      = unmangled_result
163     in
164     returnTc (possibly_mangled_result, lie_req, tvs, ids, lie_avail)
165   where
166     arity = length pats
167 \end{code}
168
169 %************************************************************************
170 %*                                                                      *
171 \subsection{Other constructors}
172 %*                                                                      *
173
174 %************************************************************************
175
176 \begin{code}
177 tcPat sig_fn pat@(ConPatIn name arg_pats) pat_ty
178   = tcConPat sig_fn pat name arg_pats pat_ty
179
180 tcPat sig_fn pat@(ConOpPatIn pat1 op _ pat2) pat_ty
181   = tcConPat sig_fn pat op [pat1, pat2] pat_ty
182 \end{code}
183
184
185 %************************************************************************
186 %*                                                                      *
187 \subsection{Records}
188 %*                                                                      *
189 %************************************************************************
190
191 \begin{code}
192 tcPat sig_fn pat@(RecPatIn name rpats) pat_ty
193   = tcAddErrCtxt (patCtxt pat)  $
194
195         -- Check the constructor itself
196     tcConstructor pat name pat_ty       `thenTc` \ (data_con, ex_tvs, dicts, lie_avail1, arg_tys) ->
197     let
198         field_tys = zipEqual "tcPat" 
199                              (map fieldLabelName (dataConFieldLabels data_con))
200                              arg_tys
201     in
202
203         -- Check the fields
204     tc_fields field_tys rpats           `thenTc` \ (rpats', lie_req, tvs, ids, lie_avail2) ->
205
206     returnTc (RecPat data_con pat_ty ex_tvs dicts rpats',
207               lie_req,
208               listToBag ex_tvs `unionBags` tvs,
209               ids,
210               lie_avail1 `plusLIE` lie_avail2)
211
212   where
213     tc_fields field_tys []
214       = returnTc ([], emptyLIE, emptyBag, emptyBag, emptyLIE)
215
216     tc_fields field_tys ((field_label, rhs_pat, pun_flag) : rpats)
217       | null matching_fields
218       = addErrTc (badFieldCon name field_label)         `thenNF_Tc_`
219         tc_fields field_tys rpats
220
221       | otherwise
222       = ASSERT( null extras )
223         tc_fields field_tys rpats       `thenTc` \ (rpats', lie_req1, tvs1, ids1, lie_avail1) ->
224
225         tcLookupGlobalValue field_label `thenNF_Tc` \ sel_id ->
226         tcPat sig_fn rhs_pat rhs_ty     `thenTc` \ (rhs_pat', lie_req2, tvs2, ids2, lie_avail2) ->
227
228         returnTc ((sel_id, rhs_pat', pun_flag) : rpats',
229                   lie_req1 `plusLIE` lie_req2,
230                   tvs1 `unionBags` tvs2,
231                   ids1 `unionBags` ids2,
232                   lie_avail1 `plusLIE` lie_avail2)
233       where
234         matching_fields   = [ty | (f,ty) <- field_tys, f == field_label]
235         (rhs_ty : extras) = matching_fields
236 \end{code}
237
238 %************************************************************************
239 %*                                                                      *
240 \subsection{Non-overloaded literals}
241 %*                                                                      *
242 %************************************************************************
243
244 \begin{code}
245 tcPat sig_fn (LitPatIn lit@(HsChar _))       pat_ty = tcSimpleLitPat lit charTy       pat_ty
246 tcPat sig_fn (LitPatIn lit@(HsIntPrim _))    pat_ty = tcSimpleLitPat lit intPrimTy    pat_ty
247 tcPat sig_fn (LitPatIn lit@(HsCharPrim _))   pat_ty = tcSimpleLitPat lit charPrimTy   pat_ty
248 tcPat sig_fn (LitPatIn lit@(HsStringPrim _)) pat_ty = tcSimpleLitPat lit addrPrimTy   pat_ty
249 tcPat sig_fn (LitPatIn lit@(HsFloatPrim _))  pat_ty = tcSimpleLitPat lit floatPrimTy  pat_ty
250 tcPat sig_fn (LitPatIn lit@(HsDoublePrim _)) pat_ty = tcSimpleLitPat lit doublePrimTy pat_ty
251
252 tcPat sig_fn (LitPatIn lit@(HsLitLit s))     pat_ty = tcSimpleLitPat lit intTy pat_ty
253         -- This one looks weird!
254 \end{code}
255
256 %************************************************************************
257 %*                                                                      *
258 \subsection{Overloaded patterns: int literals and \tr{n+k} patterns}
259 %*                                                                      *
260 %************************************************************************
261
262 \begin{code}
263 tcPat sig_fn pat@(LitPatIn lit@(HsString str)) pat_ty
264   = unifyTauTy pat_ty stringTy                  `thenTc_` 
265     tcLookupGlobalValueByKey eqClassOpKey       `thenNF_Tc` \ sel_id ->
266     newMethod (PatOrigin pat) 
267               (RealId sel_id) [stringTy]        `thenNF_Tc` \ (lie, eq_id) ->
268     let
269         comp_op = HsApp (HsVar eq_id) (HsLitOut lit stringTy)
270     in
271     returnTc (NPat lit stringTy comp_op, lie, emptyBag, emptyBag, emptyLIE)
272
273
274 tcPat sig_fn pat@(LitPatIn lit@(HsInt i)) pat_ty
275   = tcOverloadedLitPat pat lit (OverloadedIntegral i) pat_ty
276
277 tcPat sig_fn pat@(LitPatIn lit@(HsFrac f)) pat_ty
278   = tcOverloadedLitPat pat lit (OverloadedFractional f) pat_ty
279
280
281 tcPat sig_fn pat@(NPlusKPatIn name lit@(HsInt i)) pat_ty
282   = tcVarPat sig_fn name pat_ty                         `thenTc` \ bndr_id ->
283     tcLookupGlobalValueByKey geClassOpKey               `thenNF_Tc` \ ge_sel_id ->
284     tcLookupGlobalValueByKey minusClassOpKey            `thenNF_Tc` \ minus_sel_id ->
285
286     newOverloadedLit origin
287                      (OverloadedIntegral i) pat_ty      `thenNF_Tc` \ (over_lit_expr, lie1) ->
288
289     newMethod origin (RealId ge_sel_id)    [pat_ty]     `thenNF_Tc` \ (lie2, ge_id) ->
290     newMethod origin (RealId minus_sel_id) [pat_ty]     `thenNF_Tc` \ (lie3, minus_id) ->
291
292     returnTc (NPlusKPat (TcId bndr_id) lit pat_ty
293                         (SectionR (HsVar ge_id) over_lit_expr)
294                         (SectionR (HsVar minus_id) over_lit_expr),
295               lie1 `plusLIE` lie2 `plusLIE` lie3,
296               emptyBag, unitBag (name, bndr_id), emptyLIE)
297   where
298     origin = PatOrigin pat
299
300 tcPat sig_fn (NPlusKPatIn pat other) pat_ty
301   = panic "TcPat:NPlusKPat: not an HsInt literal"
302 \end{code}
303
304 %************************************************************************
305 %*                                                                      *
306 \subsection{Lists of patterns}
307 %*                                                                      *
308 %************************************************************************
309
310 Helper functions
311
312 \begin{code}
313 tcPats :: (Name -> Maybe (TcIdBndr s))  -- Info about signatures
314        -> [RenamedPat] -> [TcType s]    -- Excess 'expected types' discarded
315        -> TcM s ([TcPat s], 
316                  LIE s,                         -- Required by n+k and literal pats
317                  Bag (TcTyVar s),
318                  Bag (Name, TcIdBndr s),        -- Ids bound by the pattern
319                  LIE s)                         -- Dicts bound by the pattern
320
321 tcPats sig_fn [] tys = returnTc ([], emptyLIE, emptyBag, emptyBag, emptyLIE)
322
323 tcPats sig_fn (ty:tys) (pat:pats)
324   = tcPat sig_fn ty pat         `thenTc` \ (pat',  lie_req1, tvs1, ids1, lie_avail1) ->
325     tcPats sig_fn tys pats      `thenTc` \ (pats', lie_req2, tvs2, ids2, lie_avail2) ->
326
327     returnTc (pat':pats', lie_req1 `plusLIE` lie_req2,
328               tvs1 `unionBags` tvs2, ids1 `unionBags` ids2, 
329               lie_avail1 `plusLIE` lie_avail2)
330 \end{code}
331
332 ------------------------------------------------------
333 \begin{code}
334 tcSimpleLitPat lit lit_ty pat_ty
335   = unifyTauTy pat_ty lit_ty    `thenTc_` 
336     returnTc (LitPat lit lit_ty, emptyLIE, emptyBag, emptyBag, emptyLIE)
337
338
339 tcOverloadedLitPat pat lit over_lit pat_ty
340   = newOverloadedLit (PatOrigin pat) over_lit pat_ty    `thenNF_Tc` \ (over_lit_expr, lie1) ->
341     tcLookupGlobalValueByKey eqClassOpKey               `thenNF_Tc` \ eq_sel_id ->
342     newMethod origin (RealId eq_sel_id) [pat_ty]        `thenNF_Tc` \ (lie2, eq_id) ->
343
344     returnTc (NPat lit pat_ty (HsApp (HsVar eq_id)
345                                      over_lit_expr),
346               lie1 `plusLIE` lie2,
347               emptyBag, emptyBag, emptyLIE)
348   where
349     origin = PatOrigin pat
350 \end{code}
351
352 ------------------------------------------------------
353 \begin{code}
354 tcConstructor pat con_name pat_ty
355   =     -- Check that it's a constructor
356     tcLookupGlobalValue con_name                `thenNF_Tc` \ con_id ->
357     case isDataConId_maybe con_id of {
358         Nothing -> failWithTc (badCon con_id);
359         Just data_con ->
360
361         -- Instantiate it
362     let 
363         (tvs, theta, ex_tvs, ex_theta, arg_tys, tycon) = dataConSig data_con
364              -- Ignore the theta; overloaded constructors only
365              -- behave differently when called, not when used for
366              -- matching.
367     in
368     tcInstTyVars (ex_tvs ++ tvs)        `thenNF_Tc` \ (all_tvs', ty_args', tenv) ->
369     let
370         ex_theta' = substFlexiTheta tenv ex_theta
371         arg_tys'  = map (substFlexiTy tenv) arg_tys
372
373         n_ex_tvs  = length ex_tvs
374         ex_tvs'   = take n_ex_tvs all_tvs'
375         result_ty = mkTyConApp tycon (drop n_ex_tvs ty_args')
376     in
377     newDicts (PatOrigin pat) ex_theta'  `thenNF_Tc` \ (lie_avail, dicts) ->
378
379         -- Check overall type matches
380     unifyTauTy pat_ty result_ty         `thenTc_`
381
382     returnTc (data_con, ex_tvs', dicts, lie_avail, arg_tys')
383     }
384 \end{code}            
385
386 ------------------------------------------------------
387 \begin{code}
388 tcConPat sig_fn pat con_name arg_pats pat_ty
389   = tcAddErrCtxt (patCtxt pat)  $
390
391         -- Check the constructor itself
392     tcConstructor pat con_name pat_ty   `thenTc` \ (data_con, ex_tvs', dicts, lie_avail1, arg_tys') ->
393
394         -- Check correct arity
395     let
396         con_arity  = dataConSourceArity data_con
397         no_of_args = length arg_pats
398     in
399     checkTc (con_arity == no_of_args)
400             (arityErr "Constructor" data_con con_arity no_of_args)      `thenTc_`
401
402         -- Check arguments
403     tcPats sig_fn arg_pats arg_tys'     `thenTc` \ (arg_pats', lie_req, tvs, ids, lie_avail2) ->
404
405     returnTc (ConPat data_con pat_ty ex_tvs' dicts arg_pats',
406               lie_req,
407               listToBag ex_tvs' `unionBags` tvs,
408               ids,
409               lie_avail1 `plusLIE` lie_avail2)
410 \end{code}
411
412
413 %************************************************************************
414 %*                                                                      *
415 \subsection{Errors and contexts}
416 %*                                                                      *
417 %************************************************************************
418
419 \begin{code}
420 patCtxt pat = hang (ptext SLIT("In the pattern:")) 
421                  4 (ppr pat)
422
423 recordLabel field_label
424   = hang (hcat [ptext SLIT("When matching record field"), ppr field_label])
425          4 (hcat [ptext SLIT("with its immediately enclosing constructor")])
426
427 recordRhs field_label pat
428   = hang (ptext SLIT("In the record field pattern"))
429          4 (sep [ppr field_label, char '=', ppr pat])
430
431 badFieldCon :: Name -> Name -> SDoc
432 badFieldCon con field
433   = hsep [ptext SLIT("Constructor") <+> quotes (ppr con),
434           ptext SLIT("does not have field"), quotes (ppr field)]
435 \end{code}
436