mirror of
https://github.com/notwa/mm
synced 2024-11-05 03:19:02 -08:00
implement relative branches; fix register orders
This commit is contained in:
parent
cf413a7ab1
commit
ebc9987a38
1 changed files with 17 additions and 8 deletions
|
@ -681,10 +681,13 @@ function Parser:deref()
|
||||||
return reg
|
return reg
|
||||||
end
|
end
|
||||||
|
|
||||||
function Parser:const()
|
function Parser:const(relative)
|
||||||
if self.tt ~= 'NUM' and self.tt ~= 'DEFSYM' and self.tt ~= 'LABELSYM' then
|
if self.tt ~= 'NUM' and self.tt ~= 'DEFSYM' and self.tt ~= 'LABELSYM' then
|
||||||
self:error('expected constant')
|
self:error('expected constant')
|
||||||
end
|
end
|
||||||
|
if relative and self.tt == 'LABELSYM' then
|
||||||
|
self.tt = 'LABELREL'
|
||||||
|
end
|
||||||
local t = {self.tt, self.tok}
|
local t = {self.tt, self.tok}
|
||||||
self:advance()
|
self:advance()
|
||||||
return t
|
return t
|
||||||
|
@ -713,10 +716,10 @@ function Parser:instruction()
|
||||||
Dumper:add_instruction_5_5_16(h[1], base, ft, offset)
|
Dumper:add_instruction_5_5_16(h[1], base, ft, offset)
|
||||||
elseif h[2] == argtypes.sti then
|
elseif h[2] == argtypes.sti then
|
||||||
-- OP rt, rs, immediate
|
-- OP rt, rs, immediate
|
||||||
local rs = self:register()
|
|
||||||
self:optional_comma()
|
|
||||||
local rt = self:register()
|
local rt = self:register()
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
|
local rs = self:register()
|
||||||
|
self:optional_comma()
|
||||||
local immediate = {'LOWER', self:const()}
|
local immediate = {'LOWER', self:const()}
|
||||||
Dumper:add_instruction_5_5_16(h[1], rs, rt, immediate)
|
Dumper:add_instruction_5_5_16(h[1], rs, rt, immediate)
|
||||||
elseif h[2] == argtypes.std then
|
elseif h[2] == argtypes.std then
|
||||||
|
@ -761,7 +764,7 @@ function Parser:instruction()
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
local rt = self:register()
|
local rt = self:register()
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
local offset = self:const()
|
local offset = self:const('relative')
|
||||||
Dumper:add_instruction_5_5_16(h[1], rs, rt, offset)
|
Dumper:add_instruction_5_5_16(h[1], rs, rt, offset)
|
||||||
elseif h[2] == argtypes.stc then
|
elseif h[2] == argtypes.stc then
|
||||||
-- OP TEQ rs, rt
|
-- OP TEQ rs, rt
|
||||||
|
@ -777,9 +780,8 @@ function Parser:instruction()
|
||||||
-- OP rs, offset
|
-- OP rs, offset
|
||||||
local rs = self:register()
|
local rs = self:register()
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
local offset = self:const()
|
local offset = self:const('relative')
|
||||||
local const = h[3] or self:error('internal error: expected 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)
|
Dumper:add_instruction_5_5_16(h[1], rs, const, offset)
|
||||||
elseif h[2] == argtypes.sync then
|
elseif h[2] == argtypes.sync then
|
||||||
-- OP
|
-- OP
|
||||||
|
@ -833,7 +835,7 @@ function Parser:instruction()
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
local ft = self:register(fpu_registers)
|
local ft = self:register(fpu_registers)
|
||||||
local const = h[3] or self:error('internal error: expected const')
|
local const = h[3] or self:error('internal error: expected const')
|
||||||
Dumper:add_instruction_5_5_5_5_6(h[1], 16, fd, fs, ft, const)
|
Dumper:add_instruction_5_5_5_5_6(h[1], 16, ft, fs, fd, const)
|
||||||
elseif h[2] == argtypes.tsdd then
|
elseif h[2] == argtypes.tsdd then
|
||||||
local fd = self:register(fpu_registers)
|
local fd = self:register(fpu_registers)
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
|
@ -841,7 +843,7 @@ function Parser:instruction()
|
||||||
self:optional_comma()
|
self:optional_comma()
|
||||||
local ft = self:register(fpu_registers)
|
local ft = self:register(fpu_registers)
|
||||||
local const = h[3] or self:error('internal error: expected const')
|
local const = h[3] or self:error('internal error: expected const')
|
||||||
Dumper:add_instruction_5_5_5_5_6(h[1], 17, fd, fs, ft, const)
|
Dumper:add_instruction_5_5_5_5_6(h[1], 17, ft, fs, fd, const)
|
||||||
else
|
else
|
||||||
self:error('TODO')
|
self:error('TODO')
|
||||||
end
|
end
|
||||||
|
@ -945,6 +947,12 @@ function Dumper:desym(tok)
|
||||||
elseif tok[1] == 'LABELSYM' then
|
elseif tok[1] == 'LABELSYM' then
|
||||||
--print('(label)', tok[2])
|
--print('(label)', tok[2])
|
||||||
return self.labels[tok[2]]*4
|
return self.labels[tok[2]]*4
|
||||||
|
elseif tok[1] == 'LABELREL' then
|
||||||
|
local rel = self.labels[tok[2]] - 2 - self.line
|
||||||
|
if rel > 0x8000 or rel <= -0x8000 then
|
||||||
|
self:error('branch too far')
|
||||||
|
end
|
||||||
|
return (0x10000 + rel) % 0x10000
|
||||||
elseif tok[1] == 'DEFSYM' then
|
elseif tok[1] == 'DEFSYM' then
|
||||||
--print('(define)')
|
--print('(define)')
|
||||||
local val = self.defines[tok[2]]
|
local val = self.defines[tok[2]]
|
||||||
|
@ -1016,6 +1024,7 @@ end
|
||||||
|
|
||||||
function Dumper:dump()
|
function Dumper:dump()
|
||||||
for i, t in ipairs(self.lines) do
|
for i, t in ipairs(self.lines) do
|
||||||
|
self.line = i
|
||||||
local uw = 0
|
local uw = 0
|
||||||
local lw = 0
|
local lw = 0
|
||||||
local val = nil
|
local val = nil
|
||||||
|
|
Loading…
Reference in a new issue