Add all opcodes to the instruction representation
This commit is contained in:
parent
75b06c3a9f
commit
dd7c9d44a6
1 changed files with 50 additions and 32 deletions
|
|
@ -14,68 +14,84 @@ import Data.Word
|
||||||
import Mima.Util
|
import Mima.Util
|
||||||
import Mima.Word
|
import Mima.Word
|
||||||
|
|
||||||
data SmallOpcode = LDC | LDV | STV | ADD | AND | OR | XOR | EQL | JMP | JMN | LDIV | STIV
|
data SmallOpcode = LDC | LDV | STV | ADD | AND | OR | XOR | EQL
|
||||||
|
| JMP | JMN | LDIV | STIV | CALL | LDVR | STVR
|
||||||
deriving (Show, Eq, Ord)
|
deriving (Show, Eq, Ord)
|
||||||
|
|
||||||
instance ToText SmallOpcode where
|
instance ToText SmallOpcode where
|
||||||
toText = T.pack . show
|
toText = T.pack . show
|
||||||
|
|
||||||
allSmallOpcodes :: [SmallOpcode]
|
allSmallOpcodes :: [SmallOpcode]
|
||||||
allSmallOpcodes = [LDC, LDV, STV, ADD, AND, OR, XOR, EQL, JMP, JMN, LDIV, STIV]
|
allSmallOpcodes = [LDC, LDV, STV, ADD, AND, OR, XOR, EQL,
|
||||||
|
JMP, JMN, LDIV, STIV, CALL, LDVR, STVR]
|
||||||
|
|
||||||
getSmallOpcode :: SmallOpcode -> Word32
|
smallOpcodeToWord32 :: SmallOpcode -> Word32
|
||||||
getSmallOpcode LDC = 0
|
smallOpcodeToWord32 LDC = 0
|
||||||
getSmallOpcode LDV = 1
|
smallOpcodeToWord32 LDV = 1
|
||||||
getSmallOpcode STV = 2
|
smallOpcodeToWord32 STV = 2
|
||||||
getSmallOpcode ADD = 3
|
smallOpcodeToWord32 ADD = 3
|
||||||
getSmallOpcode AND = 4
|
smallOpcodeToWord32 AND = 4
|
||||||
getSmallOpcode OR = 5
|
smallOpcodeToWord32 OR = 5
|
||||||
getSmallOpcode XOR = 6
|
smallOpcodeToWord32 XOR = 6
|
||||||
getSmallOpcode EQL = 7
|
smallOpcodeToWord32 EQL = 7
|
||||||
getSmallOpcode JMP = 8
|
smallOpcodeToWord32 JMP = 8
|
||||||
getSmallOpcode JMN = 9
|
smallOpcodeToWord32 JMN = 9
|
||||||
getSmallOpcode LDIV = 10
|
smallOpcodeToWord32 LDIV = 10
|
||||||
getSmallOpcode STIV = 11
|
smallOpcodeToWord32 STIV = 11
|
||||||
|
smallOpcodeToWord32 CALL = 12
|
||||||
|
smallOpcodeToWord32 LDVR = 13
|
||||||
|
smallOpcodeToWord32 STVR = 14
|
||||||
|
|
||||||
smallOpcodeMap :: Map.Map Word32 SmallOpcode
|
smallOpcodeMap :: Map.Map Word32 SmallOpcode
|
||||||
smallOpcodeMap = Map.fromList [(getSmallOpcode oc, oc) | oc <- allSmallOpcodes]
|
smallOpcodeMap = Map.fromList [(smallOpcodeToWord32 so, so) | so <- allSmallOpcodes]
|
||||||
|
|
||||||
data LargeOpcode = HALT | NOT | RAR
|
data LargeOpcode = HALT | NOT | RAR | RET | LDRA | STRA
|
||||||
|
| LDSP | STSP | LDFP | STFP | ADC
|
||||||
deriving (Show, Eq, Ord)
|
deriving (Show, Eq, Ord)
|
||||||
|
|
||||||
instance ToText LargeOpcode where
|
instance ToText LargeOpcode where
|
||||||
toText = T.pack . show
|
toText = T.pack . show
|
||||||
|
|
||||||
allLargeOpcodes :: [LargeOpcode]
|
allLargeOpcodes :: [LargeOpcode]
|
||||||
allLargeOpcodes = [HALT, NOT, RAR]
|
allLargeOpcodes = [HALT, NOT, RAR, RET, LDRA, STRA, LDSP, STSP, LDFP, STFP, ADC]
|
||||||
|
|
||||||
getLargeOpcode :: LargeOpcode -> Word32
|
largeOpcodeToWord32 :: LargeOpcode -> Word32
|
||||||
getLargeOpcode HALT = 0
|
largeOpcodeToWord32 HALT = 0
|
||||||
getLargeOpcode NOT = 1
|
largeOpcodeToWord32 NOT = 1
|
||||||
getLargeOpcode RAR = 2
|
largeOpcodeToWord32 RAR = 2
|
||||||
|
largeOpcodeToWord32 RET = 3
|
||||||
|
|
||||||
|
largeOpcodeToWord32 LDRA = 4
|
||||||
|
largeOpcodeToWord32 STRA = 5
|
||||||
|
largeOpcodeToWord32 LDSP = 6
|
||||||
|
largeOpcodeToWord32 STSP = 7
|
||||||
|
largeOpcodeToWord32 LDFP = 8
|
||||||
|
largeOpcodeToWord32 STFP = 9
|
||||||
|
largeOpcodeToWord32 ADC = 10
|
||||||
|
|
||||||
largeOpcodeMap :: Map.Map Word32 LargeOpcode
|
largeOpcodeMap :: Map.Map Word32 LargeOpcode
|
||||||
largeOpcodeMap = Map.fromList [(getLargeOpcode oc, oc) | oc <- allLargeOpcodes]
|
largeOpcodeMap = Map.fromList [(largeOpcodeToWord32 lo, lo) | lo <- allLargeOpcodes]
|
||||||
|
|
||||||
data Instruction
|
data Instruction
|
||||||
= SmallInstruction !SmallOpcode !MimaAddress
|
= SmallInstruction !SmallOpcode !LargeValue
|
||||||
| LargeInstruction !LargeOpcode
|
| LargeInstruction !LargeOpcode !SmallValue
|
||||||
deriving (Show, Eq)
|
deriving (Show, Eq)
|
||||||
|
|
||||||
instance ToText Instruction where
|
instance ToText Instruction where
|
||||||
toText (SmallInstruction oc addr) = T.justifyLeft 4 ' ' (toText oc) <> " " <> addrToDec addr
|
toText (SmallInstruction oc lv) = T.justifyLeft 4 ' ' (toText oc) <> " " <> largeValueToDec lv
|
||||||
toText (LargeInstruction oc) = toText oc
|
toText (LargeInstruction oc sv)
|
||||||
|
| sv == minBound = T.justifyLeft 4 ' ' (toText oc)
|
||||||
|
| otherwise = T.justifyLeft 4 ' ' (toText oc) <> " " <> smallValueToDec sv
|
||||||
|
|
||||||
wordToInstruction :: MimaWord -> Either T.Text Instruction
|
wordToInstruction :: MimaWord -> Either T.Text Instruction
|
||||||
wordToInstruction mw = if upperOpcode mw == 0xF
|
wordToInstruction mw = if getLargeOpcode mw == 0xF
|
||||||
then parseLargeInstruction mw
|
then parseLargeInstruction mw
|
||||||
else parseSmallInstruction mw
|
else parseSmallInstruction mw
|
||||||
|
|
||||||
parseSmallInstruction :: MimaWord -> Either T.Text Instruction
|
parseSmallInstruction :: MimaWord -> Either T.Text Instruction
|
||||||
parseSmallInstruction mw = do
|
parseSmallInstruction mw = do
|
||||||
oc <- parseSmallOpcode (upperOpcode mw)
|
so <- parseSmallOpcode (getSmallOpcode mw)
|
||||||
pure $ SmallInstruction oc (address mw)
|
pure $ SmallInstruction so (getLargeValue mw)
|
||||||
|
|
||||||
-- Assumes that all bits not part of the opcode are zeroed. The opcode
|
-- Assumes that all bits not part of the opcode are zeroed. The opcode
|
||||||
-- uses the lowest four bits.
|
-- uses the lowest four bits.
|
||||||
|
|
@ -86,7 +102,9 @@ parseSmallOpcode w = case smallOpcodeMap Map.!? w of
|
||||||
<> " (" <> toHex 2 w <> ")"
|
<> " (" <> toHex 2 w <> ")"
|
||||||
|
|
||||||
parseLargeInstruction :: MimaWord -> Either T.Text Instruction
|
parseLargeInstruction :: MimaWord -> Either T.Text Instruction
|
||||||
parseLargeInstruction mw = LargeInstruction <$> parseLargeOpcode (lowerOpcode mw)
|
parseLargeInstruction mw = do
|
||||||
|
lo <- parseLargeOpcode (getLargeOpcode mw)
|
||||||
|
pure $ LargeInstruction lo (getSmallValue mw)
|
||||||
|
|
||||||
-- Assumes that all bits not part of the opcode are zeroed. The opcode
|
-- Assumes that all bits not part of the opcode are zeroed. The opcode
|
||||||
-- uses the lowest four bits.
|
-- uses the lowest four bits.
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue