1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
|
module RW.Monad where
import Data.List
import AbstractCurry.Types
import Control.Monad
import Control.Applicative
import RW.Build
data Runtime = Runtime
{ moduleName :: String
, functionLayouts :: [FunctionLayout]
, program :: CurryProg
, errors :: [String]
, illTypedDefintions :: [String]
}
data CLOptions = CLOptions
{ optStringLength :: Int
, optAlphabetLength :: Int
, optOutDir :: String
, optGenOpsFile :: Bool
, optHelp :: Bool
} deriving (Show)
newtype RWM a = RWM { runRWM :: Runtime -> (a, Runtime) }
data FunctionLayout = FunctionLayout
{ funcName :: String
, funcType :: CTypeExpr
, funcGenerator :: FunctionGenerator
}
type FunctionGenerator = CTypeDecl -> RWM [CRule]
data Naming = Naming
{ rwBaseModuleName :: String
, rwClassName :: String
, rwParametrizedModuleName :: String
}
rwNaming :: Naming
rwNaming = Naming "RW.Base" "ReadWrite" "RWOps"
instance Functor RWM where
fmap = liftA
instance Applicative RWM where
pure x = RWM $ \rt -> (x,rt)
(RWM sf) <*> (RWM sa) = RWM $ \rt -> let (fn, rt') = sf rt
(a, rt'') = sa rt'
in (fn a, rt'')
instance Monad RWM where
return = pure
a >>= f = RWM $ \rt -> let (x, rt') = runRWM a rt
in runRWM (f x) rt'
get :: RWM Runtime
get = RWM $ \rt -> (rt, rt)
put :: Runtime -> RWM ()
put rt = RWM $ \_ -> ((), rt)
getFunctionLayouts :: RWM [FunctionLayout]
getFunctionLayouts = RWM $ \rt@(Runtime{functionLayouts=fl}) -> (fl, rt)
getModuleName :: RWM String
getModuleName = RWM $ \rt@(Runtime{moduleName=mn}) -> (mn, rt)
getProgram :: RWM CurryProg
getProgram = RWM $ \rt@(Runtime{program=p}) -> (p, rt)
logIllTypedDefinition :: String -> RWM ()
logIllTypedDefinition def = RWM $ \rt@(Runtime{illTypedDefintions=defs}) -> ((), rt { illTypedDefintions = def:defs })
getIllTypedDefinitions :: Runtime -> [String]
getIllTypedDefinitions (Runtime{illTypedDefintions=defs}) = nub defs
logError :: String -> RWM ()
logError err = RWM $ \rt@(Runtime{errors=errs}) -> ((), rt { errors = err:errs })
getErrors :: Runtime -> [String]
getErrors (Runtime{errors=errs}) = errs |