[project @ 2000-10-03 08:43:00 by simonpj]
[ghc-hetmet.git] / ghc / compiler / prelude / TysWiredIn.lhs
1 %
2 % (c) The GRASP Project, Glasgow University, 1994-1998
3 %
4 \section[TysWiredIn]{Wired-in knowledge about {\em non-primitive} types}
5
6 This module is about types that can be defined in Haskell, but which
7 must be wired into the compiler nonetheless.
8
9 This module tracks the ``state interface'' document, ``GHC prelude:
10 types and operations.''
11
12 \begin{code}
13 module TysWiredIn (
14         wiredInTyCons, genericTyCons,
15
16         addrDataCon,
17         addrTy,
18         addrTyCon,
19         boolTy,
20         boolTyCon,
21         charDataCon,
22         charTy,
23         charTyCon,
24         consDataCon,
25         doubleDataCon,
26         doubleTy,
27         isDoubleTy,
28         doubleTyCon,
29         falseDataCon, falseDataConId,
30         floatDataCon,
31         floatTy,
32         isFloatTy,
33         floatTyCon,
34
35         intDataCon,
36         intTy,
37         intTyCon,
38         isIntTy,
39
40         integerTy,
41         integerTyCon,
42         smallIntegerDataCon,
43         largeIntegerDataCon,
44         isIntegerTy,
45
46         listTyCon,
47
48         mkListTy,
49         nilDataCon,
50
51         -- tuples
52         mkTupleTy,
53         tupleTyCon, tupleCon, 
54         unitTyCon, unitDataConId, pairTyCon, 
55         unboxedSingletonTyCon, unboxedSingletonDataCon,
56         unboxedPairTyCon, unboxedPairDataCon,
57
58         -- Generics
59         genUnitTyCon, genUnitDataCon, 
60         plusTyCon, inrDataCon, inlDataCon,
61         crossTyCon, crossDataCon,
62
63         stablePtrTyCon,
64         stringTy,
65         trueDataCon, trueDataConId,
66         unitTy,
67         voidTy,
68         wordDataCon,
69         wordTy,
70         wordTyCon,
71
72         isFFIArgumentTy,    -- :: Bool -> Type -> Bool
73         isFFIResultTy,      -- :: Type -> Bool
74         isFFIExternalTy,    -- :: Type -> Bool
75         isFFIDynArgumentTy, -- :: Type -> Bool
76         isFFIDynResultTy,   -- :: Type -> Bool
77         isFFILabelTy,       -- :: Type -> Bool
78         isAddrTy,           -- :: Type -> Bool
79         isForeignObjTy      -- :: Type -> Bool
80
81     ) where
82
83 #include "HsVersions.h"
84
85 import {-# SOURCE #-} MkId( mkDataConId, mkDataConWrapId )
86 import {-# SOURCE #-} Generics( mkTyConGenInfo )
87
88 -- friends:
89 import PrelNames
90 import TysPrim
91
92 -- others:
93 import Constants        ( mAX_TUPLE_SIZE )
94 import Module           ( Module, mkPrelModule )
95 import Name             ( mkWiredInTyConName, mkWiredInIdName, nameOccName )
96 import OccName          ( mkSrcOccFS, tcName, dataName, mkWorkerOcc, mkGenOcc1, mkGenOcc2 )
97 import RdrName          ( RdrName, mkPreludeQual, rdrNameOcc, rdrNameModule )
98 import DataCon          ( DataCon, StrictnessMark(..),  mkDataCon, dataConId )
99 import Var              ( TyVar, tyVarKind )
100 import TyCon            ( TyCon, AlgTyConFlavour(..), ArgVrcs, tyConDataCons,
101                           mkSynTyCon, mkTupleTyCon, 
102                           isUnLiftedTyCon, mkAlgTyConRep,tyConName
103                         )
104
105 import BasicTypes       ( Arity, RecFlag(..), EP(..), Boxity(..), isBoxed )
106
107 import Type             ( Type, mkTyConTy, mkTyConApp, mkSigmaTy, mkTyVarTys, 
108                           mkArrowKinds, boxedTypeKind, unboxedTypeKind,
109                           mkFunTy, mkFunTys, 
110                           splitTyConApp_maybe, repType, mkTyVarTy,
111                           TauType, ClassContext )
112 import Unique           ( incrUnique, mkTupleTyConUnique, mkTupleDataConUnique )
113 import PrelNames
114 import CmdLineOpts      ( opt_GlasgowExts )
115 import Array
116 import Maybe            ( fromJust )
117 import FiniteMap        ( lookupFM )
118
119 alpha_tyvar       = [alphaTyVar]
120 alpha_ty          = [alphaTy]
121 alpha_beta_tyvars = [alphaTyVar, betaTyVar]
122 \end{code}
123
124
125 %************************************************************************
126 %*                                                                      *
127 \subsection{Wired in type constructors}
128 %*                                                                      *
129 %************************************************************************
130
131 \begin{code}
132 wiredInTyCons :: [TyCon]
133 wiredInTyCons = data_tycons ++ tuple_tycons ++ unboxed_tuple_tycons
134
135 data_tycons = genericTyCons ++
136               [ addrTyCon
137               , boolTyCon
138               , charTyCon
139               , doubleTyCon
140               , floatTyCon
141               , intTyCon
142               , integerTyCon
143               , listTyCon
144               , wordTyCon
145               ]
146
147 genericTyCons :: [TyCon]
148 genericTyCons = [ plusTyCon, crossTyCon, genUnitTyCon ]
149
150
151 tuple_tycons = unitTyCon : [tupleTyCon Boxed i | i <- [2..37] ]
152 unboxed_tuple_tycons = [tupleTyCon Unboxed i | i <- [1..37] ]
153 \end{code}
154
155
156 %************************************************************************
157 %*                                                                      *
158 \subsection{mkWiredInTyCon}
159 %*                                                                      *
160 %************************************************************************
161
162 \begin{code}
163 pcNonRecDataTyCon = pcTyCon DataTyCon NonRecursive
164 pcRecDataTyCon = pcTyCon DataTyCon Recursive
165
166 pcTyCon new_or_data is_rec key rdr_name tyvars argvrcs cons
167   = tycon
168   where
169     tycon = mkAlgTyConRep name kind
170                 tyvars
171                 []              -- No context
172                 argvrcs
173                 cons
174                 (length cons)
175                 []              -- No derivings
176                 new_or_data
177                 is_rec
178                 gen_info
179
180     mod      = mkPrelModule (rdrNameModule rdr_name)
181     occ      = rdrNameOcc rdr_name
182     name     = mkWiredInTyConName key mod occ tycon
183     kind     = mkArrowKinds (map tyVarKind tyvars) boxedTypeKind
184     gen_info = mk_tc_gen_info mod key name tycon
185
186 pcDataCon :: Unique     -- DataConKey
187           -> RdrName    -- Qualified
188           -> [TyVar] -> ClassContext -> [TauType] -> TyCon -> DataCon
189 -- The unique is the first of two free uniques;
190 -- the first is used for the datacon itself and the worker;
191 -- the second is used for the wrapper.
192
193 pcDataCon wrap_key rdr_name tyvars context arg_tys tycon
194   = data_con
195   where
196     mod      = mkPrelModule (rdrNameModule rdr_name)
197     wrap_occ = rdrNameOcc rdr_name
198
199     data_con = mkDataCon wrap_name
200                 [ NotMarkedStrict | a <- arg_tys ]
201                 [ {- no labelled fields -} ]
202                 tyvars context [] [] arg_tys tycon work_id wrap_id
203
204     work_occ  = mkWorkerOcc wrap_occ
205     work_key  = incrUnique wrap_key
206     work_name = mkWiredInIdName work_key mod work_occ work_id
207     work_id   = mkDataConId work_name data_con
208
209     wrap_name = mkWiredInIdName wrap_key mod wrap_occ wrap_id
210     wrap_id   = mkDataConWrapId data_con
211 \end{code}
212
213
214 %************************************************************************
215 %*                                                                      *
216 \subsection[TysWiredIn-tuples]{The tuple types}
217 %*                                                                      *
218 %************************************************************************
219
220 \begin{code}
221 tupleTyCon :: Boxity -> Arity -> TyCon
222 tupleTyCon boxity i | i > mAX_TUPLE_SIZE = fst (mk_tuple boxity i)      -- Build one specially
223 tupleTyCon Boxed   i = fst (boxedTupleArr   ! i)
224 tupleTyCon Unboxed i = fst (unboxedTupleArr ! i)
225
226 tupleCon :: Boxity -> Arity -> DataCon
227 tupleCon boxity i | i > mAX_TUPLE_SIZE = snd (mk_tuple boxity i)        -- Build one specially
228 tupleCon Boxed   i = snd (boxedTupleArr   ! i)
229 tupleCon Unboxed i = snd (unboxedTupleArr ! i)
230
231 boxedTupleArr, unboxedTupleArr :: Array Int (TyCon,DataCon)
232 boxedTupleArr   = array (0,mAX_TUPLE_SIZE) [(i,mk_tuple Boxed i)   | i <- [0..mAX_TUPLE_SIZE]]
233 unboxedTupleArr = array (0,mAX_TUPLE_SIZE) [(i,mk_tuple Unboxed i) | i <- [0..mAX_TUPLE_SIZE]]
234
235 mk_tuple :: Boxity -> Int -> (TyCon,DataCon)
236 mk_tuple boxity arity = (tycon, tuple_con)
237   where
238         tycon   = mkTupleTyCon tc_name tc_kind arity tyvars tuple_con boxity gen_info 
239         tc_name = mkWiredInTyConName tc_uniq mod (mkSrcOccFS tcName name_str) tycon
240         tc_kind = mkArrowKinds (map tyVarKind tyvars) res_kind
241         res_kind | isBoxed boxity = boxedTypeKind
242                  | otherwise      = unboxedTypeKind
243
244         tyvars   | isBoxed boxity = take arity alphaTyVars
245                  | otherwise      = take arity openAlphaTyVars
246
247         tuple_con = pcDataCon dc_uniq rdr_name tyvars [] tyvar_tys tycon
248         tyvar_tys = mkTyVarTys tyvars
249         (mod_name, name_str) = mkTupNameStr boxity arity
250         rdr_name  = mkPreludeQual dataName mod_name name_str
251         tc_uniq   = mkTupleTyConUnique   boxity arity
252         dc_uniq   = mkTupleDataConUnique boxity arity
253         mod       = mkPrelModule mod_name
254         gen_info  = mk_tc_gen_info mod tc_uniq tc_name tycon
255
256 mk_tc_gen_info mod tc_uniq tc_name tycon
257   = gen_info
258   where
259         tc_occ_name = nameOccName tc_name
260         occ_name1   = mkGenOcc1 tc_occ_name
261         occ_name2   = mkGenOcc2 tc_occ_name
262         fn1_key     = incrUnique tc_uniq
263         fn2_key     = incrUnique fn1_key
264         name1       = mkWiredInIdName fn1_key mod occ_name1 id1
265         name2       = mkWiredInIdName fn2_key mod occ_name2 id2
266         gen_info    = mkTyConGenInfo tycon name1 name2
267         Just (EP id1 id2) = gen_info
268
269 unitTyCon     = tupleTyCon Boxed 0
270 unitDataConId = dataConId (head (tyConDataCons unitTyCon))
271
272 pairTyCon = tupleTyCon Boxed 2
273
274 unboxedSingletonTyCon   = tupleTyCon Unboxed 1
275 unboxedSingletonDataCon = tupleCon   Unboxed 1
276
277 unboxedPairTyCon   = tupleTyCon Unboxed 2
278 unboxedPairDataCon = tupleCon   Unboxed 2
279 \end{code}
280
281 %************************************************************************
282 %*                                                                      *
283 \subsection[TysWiredIn-boxed-prim]{The ``boxed primitive'' types (@Char@, @Int@, etc)}
284 %*                                                                      *
285 %************************************************************************
286
287 \begin{code}
288 -- The Void type is represented as a data type with no constructors
289 -- It's a built in type (i.e. there's no way to define it in Haskell;
290 --      the nearest would be
291 --
292 --              data Void =             -- No constructors!
293 --
294 -- ) It's boxed; there is only one value of this
295 -- type, namely "void", whose semantics is just bottom.
296 --
297 -- Haskell 98 drops the definition of a Void type, so we just 'simulate'
298 -- voidTy using ().
299 voidTy = unitTy
300 \end{code}
301
302
303 \begin{code}
304 charTy = mkTyConTy charTyCon
305
306 charTyCon   = pcNonRecDataTyCon charTyConKey charTyCon_RDR [] [] [charDataCon]
307 charDataCon = pcDataCon charDataConKey charDataCon_RDR [] [] [charPrimTy] charTyCon
308
309 stringTy = mkListTy charTy -- convenience only
310 \end{code}
311
312 \begin{code}
313 intTy = mkTyConTy intTyCon 
314
315 intTyCon = pcNonRecDataTyCon intTyConKey intTyCon_RDR [] [] [intDataCon]
316 intDataCon = pcDataCon intDataConKey mkInt_RDR [] [] [intPrimTy] intTyCon
317
318 isIntTy :: Type -> Bool
319 isIntTy = isTyCon intTyConKey
320 \end{code}
321
322 \begin{code}
323
324 wordTy = mkTyConTy wordTyCon
325
326 wordTyCon = pcNonRecDataTyCon wordTyConKey wordTyCon_RDR [] [] [wordDataCon]
327 wordDataCon = pcDataCon wordDataConKey wordDataCon_RDR [] [] [wordPrimTy] wordTyCon
328 \end{code}
329
330 \begin{code}
331 addrTy = mkTyConTy addrTyCon
332
333 addrTyCon = pcNonRecDataTyCon addrTyConKey addrTyCon_RDR [] [] [addrDataCon]
334 addrDataCon = pcDataCon addrDataConKey addrDataCon_RDR [] [] [addrPrimTy] addrTyCon
335
336 isAddrTy :: Type -> Bool
337 isAddrTy = isTyCon addrTyConKey
338 \end{code}
339
340 \begin{code}
341 floatTy = mkTyConTy floatTyCon
342
343 floatTyCon   = pcNonRecDataTyCon floatTyConKey   floatTyCon_RDR   [] [] [floatDataCon]
344 floatDataCon = pcDataCon         floatDataConKey floatDataCon_RDR [] [] [floatPrimTy] floatTyCon
345
346 isFloatTy :: Type -> Bool
347 isFloatTy = isTyCon floatTyConKey
348 \end{code}
349
350 \begin{code}
351 doubleTy = mkTyConTy doubleTyCon
352
353 isDoubleTy :: Type -> Bool
354 isDoubleTy = isTyCon doubleTyConKey
355
356 doubleTyCon   = pcNonRecDataTyCon doubleTyConKey   doubleTyCon_RDR     [] [] [doubleDataCon]
357 doubleDataCon = pcDataCon         doubleDataConKey doubleDataCon_RDR [] [] [doublePrimTy] doubleTyCon
358 \end{code}
359
360 \begin{code}
361 stablePtrTyCon
362   = pcNonRecDataTyCon stablePtrTyConKey stablePtrTyCon_RDR
363         alpha_tyvar [(True,False)] [stablePtrDataCon]
364   where
365     stablePtrDataCon
366       = pcDataCon stablePtrDataConKey stablePtrDataCon_RDR
367             alpha_tyvar [] [mkStablePtrPrimTy alphaTy] stablePtrTyCon
368 \end{code}
369
370 \begin{code}
371 foreignObjTyCon
372   = pcNonRecDataTyCon foreignObjTyConKey foreignObjTyCon_RDR
373         [] [] [foreignObjDataCon]
374   where
375     foreignObjDataCon
376       = pcDataCon foreignObjDataConKey foreignObjDataCon_RDR
377             [] [] [foreignObjPrimTy] foreignObjTyCon
378
379 isForeignObjTy :: Type -> Bool
380 isForeignObjTy = isTyCon foreignObjTyConKey
381 \end{code}
382
383 %************************************************************************
384 %*                                                                      *
385 \subsection[TysWiredIn-Integer]{@Integer@ and its related ``pairing'' types}
386 %*                                                                      *
387 %************************************************************************
388
389 @Integer@ and its pals are not really primitive.  @Integer@ itself, first:
390 \begin{code}
391 integerTy :: Type
392 integerTy = mkTyConTy integerTyCon
393
394 integerTyCon = pcNonRecDataTyCon integerTyConKey integerTyCon_RDR
395                    [] [] [smallIntegerDataCon, largeIntegerDataCon]
396
397 smallIntegerDataCon = pcDataCon smallIntegerDataConKey smallIntegerDataCon_RDR
398                 [] [] [intPrimTy] integerTyCon
399 largeIntegerDataCon = pcDataCon largeIntegerDataConKey largeIntegerDataCon_RDR
400                 [] [] [intPrimTy, byteArrayPrimTy] integerTyCon
401
402
403 isIntegerTy :: Type -> Bool
404 isIntegerTy = isTyCon integerTyConKey
405 \end{code}
406
407
408 %************************************************************************
409 %*                                                                      *
410 \subsection[TysWiredIn-ext-type]{External types}
411 %*                                                                      *
412 %************************************************************************
413
414 The compiler's foreign function interface supports the passing of a
415 restricted set of types as arguments and results (the restricting factor
416 being the )
417
418 \begin{code}
419 isFFIArgumentTy :: Bool -> Type -> Bool
420 -- Checks for valid argument type for a 'foreign import'
421 isFFIArgumentTy is_safe ty = checkRepTyCon (legalOutgoingTyCon is_safe) ty
422
423 isFFIExternalTy :: Type -> Bool
424 -- Types that are allowed as arguments of a 'foreign export'
425 isFFIExternalTy ty = checkRepTyCon legalIncomingTyCon ty
426
427 isFFIResultTy :: Type -> Bool
428 -- Types that are allowed as a result of a 'foreign import' or of a 'foreign export'
429 -- Maybe we should distinguish between import and export, but 
430 -- here we just choose the more restrictive 'incoming' predicate
431 -- But we allow () as well
432 isFFIResultTy ty = checkRepTyCon (\tc -> tc == unitTyCon || legalIncomingTyCon tc) ty
433
434 isFFIDynArgumentTy :: Type -> Bool
435 -- The argument type of a foreign import dynamic must be either Addr, or
436 -- a newtype of Addr.
437 isFFIDynArgumentTy = checkRepTyCon (== addrTyCon)
438
439 isFFIDynResultTy :: Type -> Bool
440 -- The result type of a foreign export dynamic must be either Addr, or
441 -- a newtype of Addr.
442 isFFIDynResultTy = checkRepTyCon (== addrTyCon)
443
444 isFFILabelTy :: Type -> Bool
445 -- The type of a foreign label must be either Addr, or
446 -- a newtype of Addr.
447 isFFILabelTy = checkRepTyCon (== addrTyCon)
448
449 checkRepTyCon :: (TyCon -> Bool) -> Type -> Bool
450         -- look through newtypes
451 checkRepTyCon check_tc ty = checkTyCon check_tc (repType ty)
452
453 checkTyCon :: (TyCon -> Bool) -> Type -> Bool
454 checkTyCon check_tc ty = case splitTyConApp_maybe ty of
455                                 Just (tycon, _) -> check_tc tycon
456                                 Nothing         -> False
457
458 isTyCon :: Unique -> Type -> Bool
459 isTyCon uniq ty = checkTyCon (\tc -> uniq == getUnique tc) ty
460 \end{code}
461
462 ----------------------------------------------
463 These chaps do the work; they are not exported
464 ----------------------------------------------
465
466 \begin{code}
467 legalIncomingTyCon :: TyCon -> Bool
468 -- It's illegal to return foreign objects and (mutable)
469 -- bytearrays from a _ccall_ / foreign declaration
470 -- (or be passed them as arguments in foreign exported functions).
471 legalIncomingTyCon tc
472   | getUnique tc `elem` [ foreignObjTyConKey, byteArrayTyConKey, mutableByteArrayTyConKey ] 
473   = False
474   -- It's also illegal to make foreign exports that take unboxed
475   -- arguments.  The RTS API currently can't invoke such things.  --SDM 7/2000
476   | otherwise
477   = boxedMarshalableTyCon tc
478
479 legalOutgoingTyCon :: Bool -> TyCon -> Bool
480 -- Checks validity of types going from Haskell -> external world
481 -- The boolean is true for a 'safe' call (when we don't want to
482 -- pass Haskell pointers to the world)
483 legalOutgoingTyCon be_safe tc
484   | be_safe && getUnique tc `elem` [byteArrayTyConKey, mutableByteArrayTyConKey]
485   = False
486   | otherwise
487   = marshalableTyCon tc
488
489 marshalableTyCon tc
490   =  (opt_GlasgowExts && isUnLiftedTyCon tc)
491   || boxedMarshalableTyCon tc
492
493 boxedMarshalableTyCon tc
494    = getUnique tc `elem` [ intTyConKey, int8TyConKey, int16TyConKey, int32TyConKey, int64TyConKey
495                          , wordTyConKey, word8TyConKey, word16TyConKey, word32TyConKey, word64TyConKey
496                          , floatTyConKey, doubleTyConKey
497                          , addrTyConKey, charTyConKey, foreignObjTyConKey
498                          , stablePtrTyConKey
499                          , byteArrayTyConKey, mutableByteArrayTyConKey
500                          , boolTyConKey
501                          ]
502 \end{code}
503
504
505 %************************************************************************
506 %*                                                                      *
507 \subsection[TysWiredIn-Bool]{The @Bool@ type}
508 %*                                                                      *
509 %************************************************************************
510
511 An ordinary enumeration type, but deeply wired in.  There are no
512 magical operations on @Bool@ (just the regular Prelude code).
513
514 {\em BEGIN IDLE SPECULATION BY SIMON}
515
516 This is not the only way to encode @Bool@.  A more obvious coding makes
517 @Bool@ just a boxed up version of @Bool#@, like this:
518 \begin{verbatim}
519 type Bool# = Int#
520 data Bool = MkBool Bool#
521 \end{verbatim}
522
523 Unfortunately, this doesn't correspond to what the Report says @Bool@
524 looks like!  Furthermore, we get slightly less efficient code (I
525 think) with this coding. @gtInt@ would look like this:
526
527 \begin{verbatim}
528 gtInt :: Int -> Int -> Bool
529 gtInt x y = case x of I# x# ->
530             case y of I# y# ->
531             case (gtIntPrim x# y#) of
532                 b# -> MkBool b#
533 \end{verbatim}
534
535 Notice that the result of the @gtIntPrim@ comparison has to be turned
536 into an integer (here called @b#@), and returned in a @MkBool@ box.
537
538 The @if@ expression would compile to this:
539 \begin{verbatim}
540 case (gtInt x y) of
541   MkBool b# -> case b# of { 1# -> e1; 0# -> e2 }
542 \end{verbatim}
543
544 I think this code is a little less efficient than the previous code,
545 but I'm not certain.  At all events, corresponding with the Report is
546 important.  The interesting thing is that the language is expressive
547 enough to describe more than one alternative; and that a type doesn't
548 necessarily need to be a straightforwardly boxed version of its
549 primitive counterpart.
550
551 {\em END IDLE SPECULATION BY SIMON}
552
553 \begin{code}
554 boolTy = mkTyConTy boolTyCon
555
556 boolTyCon = pcTyCon EnumTyCon NonRecursive boolTyConKey 
557                     boolTyCon_RDR [] [] [falseDataCon, trueDataCon]
558
559 falseDataCon = pcDataCon falseDataConKey false_RDR [] [] [] boolTyCon
560 trueDataCon  = pcDataCon trueDataConKey  true_RDR  [] [] [] boolTyCon
561
562 falseDataConId = dataConId falseDataCon
563 trueDataConId  = dataConId trueDataCon
564 \end{code}
565
566 %************************************************************************
567 %*                                                                      *
568 \subsection[TysWiredIn-List]{The @List@ type (incl ``build'' magic)}
569 %*                                                                      *
570 %************************************************************************
571
572 Special syntax, deeply wired in, but otherwise an ordinary algebraic
573 data types:
574 \begin{verbatim}
575 data [] a = [] | a : (List a)
576 data () = ()
577 data (,) a b = (,,) a b
578 ...
579 \end{verbatim}
580
581 \begin{code}
582 mkListTy :: Type -> Type
583 mkListTy ty = mkTyConApp listTyCon [ty]
584
585 alphaListTy = mkSigmaTy alpha_tyvar [] (mkTyConApp listTyCon alpha_ty)
586
587 listTyCon = pcRecDataTyCon listTyConKey listTyCon_RDR
588                         alpha_tyvar [(True,False)] [nilDataCon, consDataCon]
589
590 nilDataCon  = pcDataCon nilDataConKey  nil_RDR alpha_tyvar [] [] listTyCon
591 consDataCon = pcDataCon consDataConKey cons_RDR
592                 alpha_tyvar [] [alphaTy, mkTyConApp listTyCon alpha_ty] listTyCon
593 -- Interesting: polymorphic recursion would help here.
594 -- We can't use (mkListTy alphaTy) in the defn of consDataCon, else mkListTy
595 -- gets the over-specific type (Type -> Type)
596 \end{code}
597
598 %************************************************************************
599 %*                                                                      *
600 \subsection[TysWiredIn-Tuples]{The @Tuple@ types}
601 %*                                                                      *
602 %************************************************************************
603
604 The tuple types are definitely magic, because they form an infinite
605 family.
606
607 \begin{itemize}
608 \item
609 They have a special family of type constructors, of type @TyCon@
610 These contain the tycon arity, but don't require a Unique.
611
612 \item
613 They have a special family of constructors, of type
614 @Id@. Again these contain their arity but don't need a Unique.
615
616 \item
617 There should be a magic way of generating the info tables and
618 entry code for all tuples.
619
620 But at the moment we just compile a Haskell source
621 file\srcloc{lib/prelude/...} containing declarations like:
622 \begin{verbatim}
623 data Tuple0             = Tup0
624 data Tuple2  a b        = Tup2  a b
625 data Tuple3  a b c      = Tup3  a b c
626 data Tuple4  a b c d    = Tup4  a b c d
627 ...
628 \end{verbatim}
629 The print-names associated with the magic @Id@s for tuple constructors
630 ``just happen'' to be the same as those generated by these
631 declarations.
632
633 \item
634 The instance environment should have a magic way to know
635 that each tuple type is an instances of classes @Eq@, @Ix@, @Ord@ and
636 so on. \ToDo{Not implemented yet.}
637
638 \item
639 There should also be a way to generate the appropriate code for each
640 of these instances, but (like the info tables and entry code) it is
641 done by enumeration\srcloc{lib/prelude/InTup?.hs}.
642 \end{itemize}
643
644 \begin{code}
645 mkTupleTy :: Boxity -> Int -> [Type] -> Type
646 mkTupleTy boxity arity tys = mkTyConApp (tupleTyCon boxity arity) tys
647
648 unitTy    = mkTupleTy Boxed 0 []
649 \end{code}
650
651 %************************************************************************
652 %*                                                                      *
653 \subsection{Wired In Type Constructors for Representation Types}
654 %*                                                                      *
655 %************************************************************************
656
657 The following code defines the wired in datatypes cross, plus, unit
658 and c_of needed for the generic methods.
659
660 Ok, so the basic story is that for each type constructor I need to
661 create 2 things - a TyCon and a DataCon and then we are basically
662 ok. There are going to be no arguments passed to these functions
663 because -well- there is nothing to pass to these functions.
664
665 \begin{code}
666 crossTyCon :: TyCon
667 crossTyCon = pcNonRecDataTyCon crossTyConKey crossTyCon_RDR alpha_beta_tyvars [] [crossDataCon]
668
669 crossDataCon :: DataCon
670 crossDataCon = pcDataCon crossDataConKey crossDataCon_RDR alpha_beta_tyvars [] [alphaTy, betaTy] crossTyCon
671
672 plusTyCon :: TyCon
673 plusTyCon = pcNonRecDataTyCon plusTyConKey plusTyCon_RDR alpha_beta_tyvars [] [inlDataCon, inrDataCon]
674
675 inlDataCon, inrDataCon :: DataCon
676 inlDataCon = pcDataCon inlDataConKey inlDataCon_RDR alpha_beta_tyvars [] [alphaTy] plusTyCon
677 inrDataCon = pcDataCon inrDataConKey inrDataCon_RDR alpha_beta_tyvars [] [betaTy]  plusTyCon
678
679 genUnitTyCon :: TyCon   -- The "1" type constructor for generics
680 genUnitTyCon = pcNonRecDataTyCon genUnitTyConKey genUnitTyCon_RDR [] [] [genUnitDataCon]
681
682 genUnitDataCon :: DataCon
683 genUnitDataCon = pcDataCon genUnitDataConKey genUnitDataCon_RDR [] [] [] genUnitTyCon
684 \end{code}
685
686
687
688
689