Commit 81fc648d authored by sof's avatar sof
Browse files

[project @ 1997-08-03 02:30:42 by sof]

derived Show: added printing of labels for constructors with labelled fields; derived Read: added lexing of fields for constructors with labelled fields
parent 8e1115a7
...@@ -28,7 +28,7 @@ module TcGenDeriv ( ...@@ -28,7 +28,7 @@ module TcGenDeriv (
) where ) where
IMP_Ubiq() IMP_Ubiq()
IMPORT_1_3(List(partition)) IMPORT_1_3(List(partition,intersperse))
import HsSyn ( HsBinds(..), MonoBinds(..), Match(..), GRHSsAndBinds(..), import HsSyn ( HsBinds(..), MonoBinds(..), Match(..), GRHSsAndBinds(..),
GRHS(..), HsExpr(..), HsLit(..), InPat(..), Stmt(..), DoOrListComp(..), GRHS(..), HsExpr(..), HsLit(..), InPat(..), Stmt(..), DoOrListComp(..),
...@@ -38,12 +38,14 @@ import RdrHsSyn ( RdrName(..), varQual, varUnqual, mkOpApp, ...@@ -38,12 +38,14 @@ import RdrHsSyn ( RdrName(..), varQual, varUnqual, mkOpApp,
SYN_IE(RdrNameMonoBinds), SYN_IE(RdrNameHsExpr), SYN_IE(RdrNamePat) SYN_IE(RdrNameMonoBinds), SYN_IE(RdrNameHsExpr), SYN_IE(RdrNamePat)
) )
import BasicTypes ( IfaceFlavour(..) ) import BasicTypes ( IfaceFlavour(..) )
import FieldLabel ( fieldLabelName )
import Id ( GenId, isNullaryDataCon, dataConTag, import Id ( GenId, isNullaryDataCon, dataConTag,
dataConRawArgTys, fIRST_TAG, dataConRawArgTys, fIRST_TAG,
isDataCon, SYN_IE(DataCon), SYN_IE(ConTag), isDataCon, SYN_IE(DataCon), SYN_IE(ConTag),
SYN_IE(Id) ) dataConFieldLabels, SYN_IE(Id) )
import Maybes ( maybeToBool ) import Maybes ( maybeToBool )
import Name ( getOccString, getOccName, getSrcLoc, occNameString, modAndOcc, OccName, Name ) import Name ( getOccString, getOccName, getSrcLoc, occNameString,
modAndOcc, OccName, Name )
import PrimOp ( PrimOp(..) ) import PrimOp ( PrimOp(..) )
import PrelInfo -- Lots of RdrNames import PrelInfo -- Lots of RdrNames
...@@ -53,7 +55,17 @@ import Type ( eqTy, isPrimType, SYN_IE(Type) ) ...@@ -53,7 +55,17 @@ import Type ( eqTy, isPrimType, SYN_IE(Type) )
import TysPrim ( charPrimTy, intPrimTy, wordPrimTy, addrPrimTy, import TysPrim ( charPrimTy, intPrimTy, wordPrimTy, addrPrimTy,
floatPrimTy, doublePrimTy floatPrimTy, doublePrimTy
) )
import Util ( mapAccumL, zipEqual, zipWith3Equal, nOfThem, panic, assertPanic ) import Util ( mapAccumL, zipEqual, zipWithEqual,
zipWith3Equal, nOfThem, panic, assertPanic )
#if defined(__GLASGOW_HASKELL__) && __GLASGOW_HASKELL__ <= 200
intersperse :: a -> [a] -> [a]
intersperse s [] = []
intersperse s [x] = [x]
intersperse s (x:xs) = x : s : intersperse s xs
#endif
\end{code} \end{code}
%************************************************************************ %************************************************************************
...@@ -587,8 +599,10 @@ gen_Ix_binds tycon ...@@ -587,8 +599,10 @@ gen_Ix_binds tycon
) tycon_loc)))) ) tycon_loc))))
-------------------------------------------------------------- --------------------------------------------------------------
single_con_ixes = single_con_range `AndMonoBinds` single_con_ixes
single_con_index `AndMonoBinds` single_con_inRange = single_con_range `AndMonoBinds`
single_con_index `AndMonoBinds`
single_con_inRange
data_con data_con
= case maybeTyConSingleCon tycon of -- just checking... = case maybeTyConSingleCon tycon of -- just checking...
...@@ -600,13 +614,14 @@ gen_Ix_binds tycon ...@@ -600,13 +614,14 @@ gen_Ix_binds tycon
con_arity = argFieldCount data_con con_arity = argFieldCount data_con
data_con_RDR = qual_orig_name data_con data_con_RDR = qual_orig_name data_con
con_pat xs = ConPatIn data_con_RDR (map VarPatIn xs)
con_expr xs = mk_easy_App data_con_RDR xs
as_needed = take con_arity as_RDRs as_needed = take con_arity as_RDRs
bs_needed = take con_arity bs_RDRs bs_needed = take con_arity bs_RDRs
cs_needed = take con_arity cs_RDRs cs_needed = take con_arity cs_RDRs
con_pat xs = ConPatIn data_con_RDR (map VarPatIn xs)
con_expr = mk_easy_App data_con_RDR cs_needed
-------------------------------------------------------------- --------------------------------------------------------------
single_con_range single_con_range
= mk_easy_FunMonoBind tycon_loc range_RDR [TuplePatIn [con_pat as_needed, con_pat bs_needed]] [] $ = mk_easy_FunMonoBind tycon_loc range_RDR [TuplePatIn [con_pat as_needed, con_pat bs_needed]] [] $
...@@ -614,7 +629,7 @@ gen_Ix_binds tycon ...@@ -614,7 +629,7 @@ gen_Ix_binds tycon
where where
stmts = zipWith3Equal "single_con_range" mk_qual as_needed bs_needed cs_needed stmts = zipWith3Equal "single_con_range" mk_qual as_needed bs_needed cs_needed
++ ++
[ReturnStmt (con_expr cs_needed)] [ReturnStmt con_expr]
mk_qual a b c = BindStmt (VarPatIn c) mk_qual a b c = BindStmt (VarPatIn c)
(HsApp (HsVar range_RDR) (ExplicitTuple [HsVar a, HsVar b])) (HsApp (HsVar range_RDR) (ExplicitTuple [HsVar a, HsVar b]))
...@@ -625,6 +640,8 @@ gen_Ix_binds tycon ...@@ -625,6 +640,8 @@ gen_Ix_binds tycon
= mk_easy_FunMonoBind tycon_loc index_RDR [TuplePatIn [con_pat as_needed, con_pat bs_needed], con_pat cs_needed] [range_size] ( = mk_easy_FunMonoBind tycon_loc index_RDR [TuplePatIn [con_pat as_needed, con_pat bs_needed], con_pat cs_needed] [range_size] (
foldl mk_index (HsLit (HsInt 0)) (zip3 as_needed bs_needed cs_needed)) foldl mk_index (HsLit (HsInt 0)) (zip3 as_needed bs_needed cs_needed))
where where
mk_index (HsLit (HsInt 0)) (l, u, i) -- optim.
= HsApp (HsApp (HsVar index_RDR) (ExplicitTuple [HsVar l, HsVar u])) (HsVar i)
mk_index multiply_by (l, u, i) mk_index multiply_by (l, u, i)
= genOpApp ( = genOpApp (
(HsApp (HsApp (HsVar index_RDR) (ExplicitTuple [HsVar l, HsVar u])) (HsVar i)) (HsApp (HsApp (HsVar index_RDR) (ExplicitTuple [HsVar l, HsVar u])) (HsVar i))
...@@ -683,32 +700,73 @@ gen_Read_binds tycon ...@@ -683,32 +700,73 @@ gen_Read_binds tycon
data_con_RDR = qual_orig_name data_con data_con_RDR = qual_orig_name data_con
data_con_str= occNameString (getOccName data_con) data_con_str= occNameString (getOccName data_con)
con_arity = argFieldCount data_con con_arity = argFieldCount data_con
as_needed = take con_arity as_RDRs
bs_needed = take con_arity bs_RDRs
con_expr = mk_easy_App data_con_RDR as_needed con_expr = mk_easy_App data_con_RDR as_needed
nullary_con = con_arity == 0 nullary_con = con_arity == 0
labels = dataConFieldLabels data_con
lab_fields = length labels
as_needed = take con_arity as_RDRs
bs_needed
| lab_fields == 0 = take con_arity bs_RDRs
| otherwise = take (4*lab_fields + 1) bs_RDRs
-- (label, '=' and field)*n, (n-1)*',' + '{' + '}'
con_qual con_qual
= BindStmt = BindStmt
(TuplePatIn [LitPatIn (HsString data_con_str), d_Pat]) (TuplePatIn [LitPatIn (HsString data_con_str), d_Pat])
(HsApp (HsVar lex_RDR) c_Expr) (HsApp (HsVar lex_RDR) c_Expr)
tycon_loc tycon_loc
field_quals = snd (mapAccumL mk_qual d_Expr (zipEqual "as_needed" as_needed bs_needed)) str_qual str res draw_from
mk_qual draw_from (con_field, str_left) = BindStmt
(TuplePatIn [LitPatIn (HsString str), VarPatIn res])
(HsApp (HsVar lex_RDR) draw_from)
tycon_loc
read_label f
= let nm = occNameString (getOccName (fieldLabelName f))
in
[str_qual nm, str_qual SLIT("=")]
-- There might be spaces between the label and '='
field_quals
| lab_fields == 0 =
snd (mapAccumL mk_qual
d_Expr
(zipWithEqual "as_needed"
(\ con_field draw_from -> (mk_read_qual con_field,
draw_from))
as_needed bs_needed))
| otherwise =
snd $
mapAccumL mk_qual d_Expr
(zipEqual "bs_needed"
((str_qual (SLIT("{")):
concat (
intersperse ([str_qual SLIT(",")]) $
zipWithEqual
"field_quals"
(\ as b -> as ++ [b])
-- The labels
(map read_label labels)
-- The fields
(map mk_read_qual as_needed))) ++ [str_qual (SLIT("}"))])
bs_needed)
mk_qual draw_from (f, str_left)
= (HsVar str_left, -- what to draw from down the line... = (HsVar str_left, -- what to draw from down the line...
f str_left draw_from)
mk_read_qual con_field res draw_from =
BindStmt BindStmt
(TuplePatIn [VarPatIn con_field, VarPatIn str_left]) (TuplePatIn [VarPatIn con_field, VarPatIn res])
(HsApp (HsApp (HsVar readsPrec_RDR) (HsLit (HsInt 10))) draw_from) (HsApp (HsApp (HsVar readsPrec_RDR) (HsLit (HsInt 10))) draw_from)
tycon_loc tycon_loc
)
result_expr = ExplicitTuple [con_expr, if null bs_needed result_expr = ExplicitTuple [con_expr, if null bs_needed
then d_Expr then d_Expr
else HsVar (last bs_needed)] else HsVar (last bs_needed)]
stmts = (con_qual : field_quals) ++ [ReturnStmt result_expr] stmts = con_qual:field_quals ++ [ReturnStmt result_expr]
read_paren_arg read_paren_arg
= if nullary_con then -- must be False (parens are surely optional) = if nullary_con then -- must be False (parens are surely optional)
...@@ -721,6 +779,7 @@ gen_Read_binds tycon ...@@ -721,6 +779,7 @@ gen_Read_binds tycon
HsLam (mk_easy_Match tycon_loc [c_Pat] [] $ HsLam (mk_easy_Match tycon_loc [c_Pat] [] $
HsDo ListComp stmts tycon_loc) HsDo ListComp stmts tycon_loc)
) (HsVar b_RDR) ) (HsVar b_RDR)
\end{code} \end{code}
%************************************************************************ %************************************************************************
...@@ -752,18 +811,53 @@ gen_Show_binds tycon ...@@ -752,18 +811,53 @@ gen_Show_binds tycon
bs_needed = take con_arity bs_RDRs bs_needed = take con_arity bs_RDRs
con_pat = ConPatIn data_con_RDR (map VarPatIn bs_needed) con_pat = ConPatIn data_con_RDR (map VarPatIn bs_needed)
nullary_con = con_arity == 0 nullary_con = con_arity == 0
labels = dataConFieldLabels data_con
lab_fields = length labels
show_con show_con
= let nm = occNameString (getOccName data_con) = let nm = occNameString (getOccName data_con)
space_maybe = if nullary_con then _NIL_ else SLIT(" ") space_ocurly_maybe
| nullary_con = _NIL_
| lab_fields == 0 = SLIT(" ")
| otherwise = SLIT("{")
in
mk_showString_app (nm _APPEND_ space_ocurly_maybe)
show_all con fs
= let
ccurly_maybe
| lab_fields > 0 = [mk_showString_app (SLIT("}"))]
| otherwise = []
in in
HsApp (HsVar showString_RDR) (HsLit (HsString (nm _APPEND_ space_maybe))) con:fs ++ ccurly_maybe
show_thingies = show_con : (spacified real_show_thingies) show_thingies = show_all show_con real_show_thingies_with_labs
real_show_thingies show_label l
= [ HsApp (HsApp (HsVar showsPrec_RDR) (HsLit (HsInt 10))) (HsVar b) = let nm = occNameString (getOccName (fieldLabelName l))
in
mk_showString_app (nm _APPEND_ SLIT("="))
mk_showString_app str = HsApp (HsVar showString_RDR)
(HsLit (HsString str))
real_show_thingies =
[ HsApp (HsApp (HsVar showsPrec_RDR) (HsLit (HsInt 10))) (HsVar b)
| b <- bs_needed ] | b <- bs_needed ]
real_show_thingies_with_labs
| lab_fields == 0 = intersperse (HsVar showSpace_RDR) real_show_thingies
| otherwise = --Assumption: no of fields == no of labelled fields
-- (and in same order)
concat $
intersperse ([mk_showString_app (_CONS_ ',' _NIL_ )]) $ -- Using SLIT() is not cool here.
zipWithEqual "gen_Show_binds"
(\ a b -> [a,b])
(map show_label labels)
real_show_thingies
in in
if nullary_con then -- skip the showParen junk... if nullary_con then -- skip the showParen junk...
ASSERT(null bs_needed) ASSERT(null bs_needed)
...@@ -772,10 +866,6 @@ gen_Show_binds tycon ...@@ -772,10 +866,6 @@ gen_Show_binds tycon
([a_Pat, con_pat], ([a_Pat, con_pat],
showParen_Expr (HsPar (genOpApp a_Expr ge_RDR (HsLit (HsInt 10)))) showParen_Expr (HsPar (genOpApp a_Expr ge_RDR (HsLit (HsInt 10))))
(HsPar (nested_compose_Expr show_thingies))) (HsPar (nested_compose_Expr show_thingies)))
where
spacified [] = []
spacified [x] = [x]
spacified (x:xs) = (x : (HsVar showSpace_RDR) : spacified xs)
\end{code} \end{code}
%************************************************************************ %************************************************************************
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment