git @ Cat's Eye Technologies ZOWIE / dcce714
No "CPU". Commit, rollback etc are functions from State to State. Chris Pressey 11 months ago
1 changed file(s) with 34 addition(s) and 16 deletion(s). Raw diff Collapse all Expand all
99 readMem mem addr = Map.findWithDefault 0 addr mem
1010 writeMem mem addr value = Map.insert addr value mem
1111
12 data Instruction = Immediate Addr Value
13 | Direct Addr Addr
14 | Indirect Addr Addr Value
15 deriving (Show, Ord, Eq)
16
17 data State = State {
18 pc :: Addr,
19 mem :: Memory,
20 prog :: [Instruction],
21 saved :: Maybe State
22 } deriving (Show, Ord, Eq)
23
1224 data Register = TtyRegister
1325 | BeginTransactionRegister
1426 | CommitRegister
1830 | MultiplicationRegister
1931 | NegationRegister
2032 | RegularRegister Addr
21
22 type CPU = Integer
23
24 data State = State {
25 cpu :: CPU,
26 mem :: Memory
27 } deriving (Show, Ord, Eq)
2833
2934
3035 mapRegister 0 = TtyRegister
3742 mapRegister 7 = NegationRegister
3843 mapRegister x = RegularRegister x
3944
45
4046 readAddr :: State -> Addr -> IO Value
41 readAddr state@State{ cpu=cpu, mem=mem } addr =
47 readAddr state@State{ mem=mem } addr =
4248 case mapRegister addr of
4349 TtyRegister -> do
4450 i <- readLn
5258 NegationRegister -> return 7
5359 RegularRegister x -> return (readMem mem x)
5460
61
5562 writeAddr :: State -> Addr -> Value -> IO State
56 writeAddr state@State{ cpu=cpu, mem=mem } addr payload =
63 writeAddr state@State{ mem=mem } addr payload =
5764 case mapRegister addr of
5865 TtyRegister -> do
5966 print payload
6067 return state
6168 BeginTransactionRegister ->
62 return state{ cpu=(beginTransaction cpu) }
69 return $ beginTransaction state
6370 CommitRegister ->
64 return state{ cpu=(if payload > 0 then commit cpu else rollback cpu) }
71 return $ if payload > 0 then commit state else rollback state
6572 CommitAndRepeatRegister ->
66 return state{ cpu=(if payload > 0 then commitAndRepeat cpu else commit cpu) }
73 return $ if payload > 0 then commitAndRepeat state else commit state
6774 AdditionRegister ->
6875 return state{ mem=(writeMem mem 8 ((readMem mem 8) + payload)) }
6976 SubtractionRegister ->
7683 return state{ mem=(writeMem mem x payload) }
7784
7885
79 beginTransaction x = x
86 beginTransaction :: State -> State
87 beginTransaction state@State{} =
88 state{ saved=(Just state) }
8089
81 commit x = x
8290
83 commitAndRepeat x = x
91 rollback :: State -> State
92 rollback state@State{ pc=pc, saved=(Just previous) } =
93 previous{ pc=pc }
8494
85 rollback x = x
95
96 commit :: State -> State
97 commit state@State{ saved=(Just previous) } =
98 state{ saved=(saved previous) }
99
100
101 commitAndRepeat :: State -> State
102 commitAndRepeat state@State{ saved=(Just previous) } =
103 state{ pc=((pc previous) - 1) }