1
0
Fork 0
mirror of https://github.com/notwa/lips synced 2024-04-23 22:53:22 -07:00
lips/lips/util.lua

96 lines
2.3 KiB
Lua

local floor = math.floor
local open = io.open
local function readfile(fn, binary)
local mode = binary and 'rb' or 'r'
local f = open(fn, mode)
if not f then
local kind = binary and 'binary' or 'assembly'
error('could not open '..kind..' file for reading: '..tostring(fn), 2)
end
local data = f:read('*a')
f:close()
return data
end
local function bitrange(x, lower, upper)
return floor(x / 2^lower) % 2^(upper - lower + 1)
end
local function parent(t)
local mt = getmetatable(t)
if mt == nil then
return nil
end
return mt.__index
end
local function signs(s)
local start, end_ = s:find('[+-]+')
if start ~= 1 then
return 0
end
if s:sub(1, 1) == '+' then
return end_
elseif s:sub(1, 1) == '-' then
return -end_
end
end
-- http://stackoverflow.com/a/9279009
local loadcode
if setfenv and loadstring then -- 5.1, JIT
loadcode = function(code, environment)
local f = assert(loadstring(code))
setfenv(f, environment)
return f
end
else -- 5.2, 5.3
loadcode = function(code, environment)
return assert(load(code, nil, 't', environment))
end
end
local data_sizes = {
BYTE = 1,
HALFWORD = 2,
WORD = 4,
}
local function measure_data(s)
assert(s and s.type == '!DATA', 'Internal Error: expected !DATA statement')
local n = 0
for i, t in ipairs(s) do
if t.tt == 'LABELSYM' then
n = n + 4
elseif t.tt == 'NUM' then
if t.size == nil then
error('Internal Error: unspecified data size in NUM')
end
local size = data_sizes[t.size]
if size == nil then
error('Internal Error: unknown data size in NUM, got '..tostring(t.size))
end
n = n + size
elseif t.tt == 'WORDS' then
n = n + #t.tok * 4
elseif t.tt == 'HALFWORDS' then
n = n + #t.tok * 2
elseif t.tt == 'BYTES' then
n = n + #t.tok * 1
else
error('Internal Error: unknown data type in !DATA, got '..tostring(t.tt))
end
end
return n
end
return {
readfile = readfile,
bitrange = bitrange,
parent = parent,
signs = signs,
loadcode = loadcode,
measure_data = measure_data,
}