1
0
Fork 0
mirror of https://github.com/notwa/mm synced 2024-11-05 01:29:03 -08:00

add fpu registers and basic moves

This commit is contained in:
Connor Olding 2015-11-20 13:28:10 -08:00
parent 8407c4e016
commit 301bfc99f8

View file

@ -14,7 +14,13 @@ local registers = {
'T8', 'T9', 'K0', 'K1', 'GP', 'SP', 'S8', 'RA',
}
local all_registers = registers -- TODO
local fpu_registers = {
[0]=
'F0', 'F1', 'F2', 'F3', 'F4', 'F5', 'F6', 'F7',
'F8', 'F9', 'F10', 'F11', 'F12', 'F13', 'F14', 'F15',
'F16', 'F17', 'F18', 'F19', 'F20', 'F21', 'F22', 'F23',
'F24', 'F25', 'F26', 'F27', 'F28', 'F29', 'F30', 'F31',
}
local all_instructions = {
'ADD', 'ADDI', 'ADDIU', 'ADDU',
@ -168,6 +174,14 @@ local all_tokens = {
'SEP',
}
local all_registers = {}
for k, v in pairs(registers) do
all_registers[k] = v
end
for k, v in pairs(fpu_registers) do
all_registers[k + 32] = v
end
-- set up reverse table lookups
local function revtable(t)
for k, v in pairs(t) do
@ -176,12 +190,13 @@ local function revtable(t)
end
revtable(registers)
revtable(fpu_registers)
revtable(all_registers)
revtable(all_instructions)
revtable(all_tokens)
local argtypes = {
bro = 'base rt offset',
bto = 'base rt offset',
sti = 'rs rt immediate',
std = 'rs rt rd', -- ending with 5 unset bits and a const
st = 'rs rt', -- ending with 10 unset bits and a const
@ -197,11 +212,27 @@ local argtypes = {
mf = 'rd', -- 10 unset bits on left, 5 on right, ending with a const
jalr= 'rs rd', -- 5 unset bits inbetween, 5 on right, ending with a const
code= 'code', -- ending with a const
movf= 'rd fs', -- starting with const, ending with 11 unset bits
bfo = 'base fs offset',
}
local at = argtypes -- temporary shorthand
local instruction_handlers = {
CFC1 = {17, at.movf, 2},
CTC1 = {17, at.movf, 6},
DMFC1 = {17, at.movf, 1},
DMTC1 = {17, at.movf, 5},
MFC0 = {16, at.movf, 0},
MFC1 = {16, at.movf, 0},
MTC0 = {17, at.movf, 4},
MTC1 = {17, at.movf, 4},
LDC1 = {53, at.bfo},
LWC1 = {49, at.bfo},
SDC1 = {61, at.bfo},
SWC1 = {57, at.bfo},
--
@ -253,29 +284,29 @@ local instruction_handlers = {
NOP = { 0, at.code, 0},
LB = {32, at.bro},
LBU = {36, at.bro},
LD = {55, at.bro},
LDL = {26, at.bro},
LDR = {27, at.bro},
LH = {33, at.bro},
LHU = {37, at.bro},
LL = {48, at.bro},
LLD = {52, at.bro},
LW = {35, at.bro},
LWL = {34, at.bro},
LWR = {38, at.bro},
LWU = {39, at.bro},
SB = {40, at.bro},
SC = {56, at.bro},
SCD = {60, at.bro},
SD = {63, at.bro},
SDL = {44, at.bro},
SDR = {45, at.bro},
SH = {41, at.bro},
SW = {43, at.bro},
SWL = {42, at.bro},
SWR = {46, at.bro},
LB = {32, at.bto},
LBU = {36, at.bto},
LD = {55, at.bto},
LDL = {26, at.bto},
LDR = {27, at.bto},
LH = {33, at.bto},
LHU = {37, at.bto},
LL = {48, at.bto},
LLD = {52, at.bto},
LW = {35, at.bto},
LWL = {34, at.bto},
LWR = {38, at.bto},
LWU = {39, at.bto},
SB = {40, at.bto},
SC = {56, at.bto},
SCD = {60, at.bto},
SD = {63, at.bto},
SDL = {44, at.bto},
SDR = {45, at.bto},
SH = {41, at.bto},
SW = {43, at.bto},
SWL = {42, at.bto},
SWR = {46, at.bto},
ADDI = { 8, at.sti},
ADDIU = { 9, at.sti},
@ -625,7 +656,8 @@ function Parser:directive()
end
end
function Parser:register()
function Parser:register(t)
t = t or registers
if self.tt ~= 'REG' then
if self.tt == 'NUM' and self.tok == '0' then
-- i don't think cajeasm actually does this
@ -636,6 +668,9 @@ function Parser:register()
end
end
local reg = self.tok
if not t[reg] then
self:error('wrong type of register')
end
self:advance()
return reg
end
@ -665,16 +700,20 @@ function Parser:instruction()
if h == nil then
self:error('undefined instruction')
elseif h[2] == nil then
-- OP
Dumper:add_instruction_26(h[1])
elseif h[2] == argtypes.bro then
elseif h[2] == argtypes.bto then
-- OP rt, offset(base)
local rt = self:register()
self:optional_comma()
local offset = {'LOWER', self:const()}
local base = self:deref()
Dumper:add_instruction_5_5_16(h[1], base, rt, offset)
elseif h[2] == argtypes.bfo then
-- OP ft, offset(base)
local ft = self:register(fpu_registers)
self:optional_comma()
local offset = {'LOWER', self:const()}
local base = self:deref()
Dumper:add_instruction_5_5_16(h[1], base, rt, offset)
elseif h[2] == argtypes.sti then
-- OP rt, rs, immediate
local rs = self:register()
@ -743,6 +782,7 @@ function Parser:instruction()
self:optional_comma()
local offset = self:const()
local const = h[3] or self:error('internal error: expected const')
-- FIXME: branches are relative
Dumper:add_instruction_5_5_16(h[1], rs, const, offset)
elseif h[2] == argtypes.sync then
-- OP
@ -775,6 +815,19 @@ function Parser:instruction()
-- OP
local const = h[3] or self:error('internal error: expected const')
Dumper:add_instruction_26(h[1], const)
elseif h[2] == argtypes.movf then
local rt = self:register()
self:optional_comma()
local rd
if name == 'MFC0' or name == 'MTC0' then
-- OP rt, rd
rd = self:register()
else
-- OP rt, fs
rd = self:register(fpu_registers)
end
local const = h[3] or self:error('internal error: expected const')
Dumper:add_instruction_5_5_5_5_6(h[1], const, rt, rd, 0, 0)
else
self:error('TODO')
end