4import Control.Monad.State hiding(lift)
8data LVar = Loc Int | Glob Name
12 | LApp Bool LExp [LExp] -- True = tail call
13 | LLazyApp Name [LExp] -- True = tail call
15 | LForce LExp -- make sure Exp is evaluted
16 | LLet Name LExp LExp -- name just for pretty printing
17 | LLam [Name] LExp -- lambda, lifted out before compiling
18 | LProj LExp Int -- projection
19 | LCon Int Name [LExp]
22 | LForeign FLang FType String [(FType, LExp)]
28-- Primitive operators. Backends are not *required* to implement all
29-- of these, but should report an error if they are unable
31data PrimFn = LPlus | LMinus | LTimes | LDiv | LMod
32 | LAnd | LOr | LXOr | LCompl | LSHL| LSHR
33 | LEq | LLt | LLe | LGt | LGe
34 | LFPlus | LFMinus | LFTimes | LFDiv
35 | LFEq | LFLt | LFLe | LFGt | LFGe
36 | LBPlus | LBMinus | LBDec | LBTimes | LBDiv | LBMod
37 | LBEq | LBLt | LBLe | LBGt | LBGe
38 | LStrConcat | LStrLt | LStrEq | LStrLen
39 | LIntFloat | LFloatInt | LIntStr | LStrInt | LFloatStr | LStrFloat
40 | LIntBig | LBigInt | LStrBig | LBigStr
41 | LPrintNum | LPrintStr | LReadStr
45 | LW8Plus | LW8Minus | LW8Times
46 | LW16Plus | LW16Minus | LW16Times
48 | LFExp | LFLog | LFSin | LFCos | LFTan | LFASin | LFACos | LFATan
49 | LFSqrt | LFFloor | LFCeil
51 | LStrHead | LStrTail | LStrCons | LStrIndex | LStrRev
52 | LStdIn | LStdOut | LStdErr
55 | LPar -- evaluate argument anywhere, possibly on another
56 -- core or another machine. 'id' is a valid implementation
61-- Supported target languages for foreign calls
66data FType = FInt | FChar | FString | FUnit | FPtr | FDouble | FAny
69data LAlt = LConCase Int Name [Name] LExp
70 | LConstCase Const LExp
74data LDecl = LFun [LOpt] Name [Name] LExp -- options, name, arg names, def
75 | LConstructor Name Int Int -- constructor name, tag, arity
78type LDefs = Ctxt LDecl
80data LOpt = Inline | NoInline
83addTags :: Int -> [(Name, LDecl)] -> (Int, [(Name, LDecl)])
84addTags i ds = tag i ds []
85 where tag i ((n, LConstructor n' (-1) a) : as) acc
86 = tag (i + 1) as ((n, LConstructor n' i a) : acc)
87 tag i ((n, LConstructor n' t a) : as) acc
88 = tag i as ((n, LConstructor n' t a) : acc)
89 tag i (x : as) acc = tag i as (x : acc)
90 tag i [] acc = (i, reverse acc)
92data LiftState = LS Name Int [(Name, LDecl)]
94lname (NS n x) i = NS (lname n i) x
95lname (UN n) i = MN i n
96lname x i = MN i (show x)
98liftAll :: [(Name, LDecl)] -> [(Name, LDecl)]
99liftAll xs = concatMap (\ (x, d) -> lambdaLift x d) xs
101lambdaLift :: Name -> LDecl -> [(Name, LDecl)]
102lambdaLift n (LFun _ _ args e)
103 = let (e', (LS _ _ decls)) = runState (lift args e) (LS n 0 []) in
104 (n, LFun [] n args e') : decls
105lambdaLift n x = [(n, x)]
107getNextName :: State LiftState Name
108getNextName = do LS n i ds <- get
109 put (LS n (i + 1) ds)
112addFn :: Name -> LDecl -> State LiftState ()
113addFn fn d = do LS n i ds <- get
114 put (LS n i ((fn, d) : ds))
116lift :: [Name] -> LExp -> State LiftState LExp
117lift env (LV v) = return (LV v) -- Lifting happens before these can exist...
118lift env (LApp tc (LV (Glob n)) args) = do args' <- mapM (lift env) args
119 return (LApp tc (LV (Glob n)) args')
120lift env (LApp tc f args) = do f' <- lift env f
122 addFn fn (LFun [Inline] fn env f')
123 args' <- mapM (lift env) args
124 return (LApp tc (LV (Glob fn)) (map (LV . Glob) env ++ args'))
125lift env (LLazyApp n args) = do args' <- mapM (lift env) args
126 return (LLazyApp n args')
127lift env (LLazyExp (LConst c)) = return (LConst c)
128-- lift env (LLazyExp (LApp tc (LV (Glob f)) args))
129-- = lift env (LLazyApp f args)
130lift env (LLazyExp e) = do e' <- lift env e
131 let usedArgs = nub $ usedIn env e'
133 addFn fn (LFun [NoInline] fn usedArgs e')
134 return (LLazyApp fn (map (LV . Glob) usedArgs))
135lift env (LForce e) = do e' <- lift env e
137lift env (LLet n v e) = do v' <- lift env v
138 e' <- lift (env ++ [n]) e
139 return (LLet n v' e')
140lift env (LLam args e) = do e' <- lift (env ++ args) e
141 let usedArgs = nub $ usedIn env e'
143 addFn fn (LFun [Inline] fn (usedArgs ++ args) e')
144 return (LApp False (LV (Glob fn)) (map (LV . Glob) usedArgs))
145lift env (LProj t i) = do t' <- lift env t
147lift env (LCon i n args) = do args' <- mapM (lift env) args
148 return (LCon i n args')
149lift env (LCase e alts) = do alts' <- mapM liftA alts
151 return (LCase e' alts')
153 liftA (LConCase i n args e) = do e' <- lift (env ++ args) e
154 return (LConCase i n args e')
155 liftA (LConstCase c e) = do e' <- lift env e
156 return (LConstCase c e')
157 liftA (LDefaultCase e) = do e' <- lift env e
158 return (LDefaultCase e')
159lift env (LConst c) = return (LConst c)
160lift env (LForeign l t s args) = do args' <- mapM (liftF env) args
161 return (LForeign l t s args')
163 liftF env (t, e) = do e' <- lift env e
165lift env (LOp f args) = do args' <- mapM (lift env) args
167lift env (LError str) = return $ LError str
168lift env LNothing = return $ LNothing
170-- Return variables in list which are used in the expression
172usedArg env n | n `elem` env = [n]
175usedIn :: [Name] -> LExp -> [Name]
176usedIn env (LV (Glob n)) = usedArg env n
177usedIn env (LApp _ e args) = usedIn env e ++ concatMap (usedIn env) args
178usedIn env (LLazyApp n args) = concatMap (usedIn env) args ++ usedArg env n
179usedIn env (LLazyExp e) = usedIn env e
180usedIn env (LForce e) = usedIn env e
181usedIn env (LLet n v e) = usedIn env v ++ usedIn (env \\ [n]) e
182usedIn env (LLam ns e) = usedIn (env \\ ns) e
183usedIn env (LCon i n args) = concatMap (usedIn env) args
184usedIn env (LProj t i) = usedIn env t
185usedIn env (LCase e alts) = usedIn env e ++ concatMap (usedInA env) alts
186 where usedInA env (LConCase i n ns e) = usedIn env e
187 usedInA env (LConstCase c e) = usedIn env e
188 usedInA env (LDefaultCase e) = usedIn env e
189usedIn env (LForeign _ _ _ args) = concatMap (usedIn env) (map snd args)
190usedIn env (LOp f args) = concatMap (usedIn env) args
193instance Show LExp where
194 show e = show' [] e where
195 show' env (LV (Loc i)) = env!!i
196 show' env (LV (Glob n)) = show n
197 show' env (LLazyApp e args) = show e ++ "|(" ++
198 showSep ", " (map (show' env) args) ++")"
199 show' env (LApp _ e args) = show' env e ++ "(" ++
200 showSep ", " (map (show' env) args) ++")"
201 show' env (LLazyExp e) = "%lazy(" ++ show' env e ++ ")"
202 show' env (LForce e) = "%force(" ++ show' env e ++ ")"
203 show' env (LLet n v e) = "let " ++ show n ++ " = " ++ show' env v ++ " in " ++
204 show' (env ++ [show n]) e
205 show' env (LLam args e) = "\\ " ++ showSep "," (map show args) ++ " => " ++
206 show' (env ++ (map show args)) e
207 show' env (LProj t i) = show t ++ "!" ++ show i
208 show' env (LCon i n args) = show n ++ ")" ++ showSep ", " (map (show' env) args) ++ ")"
209 show' env (LCase e alts) = "case " ++ show' env e ++ " of {\n\t" ++
210 showSep "\n\t| " (map (showAlt env) alts)
211 show' env (LConst c) = show c
212 show' env (LForeign lang ty n args)
213 = "foreign " ++ n ++ "(" ++ showSep ", " (map (show' env) (map snd args)) ++ ")"
214 show' env (LOp f args) = show f ++ "(" ++ showSep ", " (map (show' env) args) ++ ")"
215 show' env (LError str) = "error " ++ show str
216 show' env LNothing = "____"
218 showAlt env (LConCase _ n args e)
219 = show n ++ "(" ++ showSep ", " (map show args) ++ ") => "
221 showAlt env (LConstCase c e) = show c ++ " => " ++ show' env e
222 showAlt env (LDefaultCase e) = "_ => " ++ show' env e
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