diff options
-rw-r--r-- | package.yaml | 1 | ||||
-rw-r--r-- | src/Suem.hs | 52 |
2 files changed, 39 insertions, 14 deletions
diff --git a/package.yaml b/package.yaml index 23821e0..4894b86 100644 --- a/package.yaml +++ b/package.yaml @@ -10,6 +10,7 @@ ghc-options: -O2 -Wall -static -optl-static -optl-pthread dependencies: - base >= 4.7 && < 5 +- vector - bytestring - optparse-applicative diff --git a/src/Suem.hs b/src/Suem.hs index 0288d62..0602196 100644 --- a/src/Suem.hs +++ b/src/Suem.hs @@ -1,7 +1,9 @@ module Suem (Config(..), ConfigSocket(..), suem) where +import qualified Data.Vector.Unboxed as V import qualified Data.ByteString as B import Data.Word +import Data.Bits data Registers = Registers { @@ -15,15 +17,15 @@ data Registers = Registers { data Machine = Machine { regs :: Registers, - ram :: B.ByteString, - rom :: B.ByteString + ram :: V.Vector Word8, + rom :: V.Vector Word8 } getByte :: Machine -> Int -> Word8 -getByte m a | a < 0x8 = B.index (rom m) a - | a < 0x7e0000 = if B.length (ram m) >= a then B.index (ram m) a +getByte m a | a < 0x8 = rom m V.! a + | a < 0x7e0000 = if V.length (ram m) >= a then ram m V.! a else 0xff - | a < 0x800000 = B.index (rom m) (a - 0x7e0000) + | a < 0x800000 = rom m V.! (a - 0x7e0000) | otherwise = 0xff getWord :: Machine -> Int -> Word16 -- TODO: only even addresses are allowed @@ -49,18 +51,40 @@ data Config = Config Int -- frequence (Maybe ConfigSocket) (Maybe ConfigSocket) +doCommand :: Word16 -> Machine -> Machine +doCommand cmd m = case cmd .&. 0xf000 of + 0 -> if testBit cmd 7 + then let rega = (shiftR cmd 9) .&. 0x7 in + m + else m + 0x1000 -> m + 0x2000 -> m + 0x3000 -> m + 0x4000 -> m + 0x5000 -> m + 0x6000 -> m + 0x7000 -> m + 0x8000 -> m + 0x9000 -> m + 0xb000 -> m + 0xc000 -> m + 0xd000 -> m + 0xe000 -> m + _ -> error "Bad command" + + runMachine :: Machine -> IO () -runMachine _ = do - putStrLn "Machine created." +runMachine m = do + runMachine $ doCommand (getWord m $ fromIntegral $ pc $ regs m) m -makeMachine :: B.ByteString -> Int -> Machine -makeMachine romData ramSize = Machine regs ramData romData - where ramData = (B.replicate ramSize 0) - regs = (Registers (getLong m 0x7e0004) 0x2700 (replicate 8 0) - (replicate 7 0) 0 (getLong m 0x7e0000)) - m = Machine (Registers 0 0 [] [] 0 0) B.empty romData +makeMachine :: V.Vector Word8 -> Int -> Machine +makeMachine romData ramSize = Machine rs rd romData + where rd = V.replicate ramSize 0 + rs = Registers (getLong m 0x7e0004) 0x2700 (replicate 8 0) + (replicate 7 0) 0 (getLong m 0x7e0000) + m = Machine (Registers 0 0 [] [] 0 0) V.empty romData suem :: Config -> IO () suem (Config _ ramSize romPath _ _ _ _ _ _ _ _) = do romData <- B.readFile romPath - runMachine (makeMachine romData ramSize) + runMachine (makeMachine (V.fromList $ B.unpack $ romData) ramSize) |