commit - 8cd27d016af5c15375e30fd490a71a5cd6a803e9
commit + e0074095e24797bb794ffd465b0b2a6442caa8d9
blob - 2e181e40bb6bac090d4115b2baae058e2d7445dc
blob + 7de524159eeb3940ea7270e030f030511e494f59
--- tools/6c
+++ tools/6c
local TOKEN_STRING = 18
local TOKEN_SEMICOLON = 19
local TOKEN_HASH = 20
+local TOKEN_COMMA = 21
+local TOKEN_HLT = 22
+local TOKEN_RET = 23
+local TOKEN_CLI = 24
+local TOKEN_STI = 25
+local TOKEN_AH = 26
+local TOKEN_AL = 27
+local TOKEN_BH = 28
+local TOKEN_BL = 29
+local TOKEN_CL = 30
+local TOKEN_CH = 31
+local TOKEN_DL = 32
+local TOKEN_DH = 33
+local TOKEN_MOV = 34
+local TOKEN_HEXADECIMAL = 35
local function issymbol(char)
if char == "{" or
char == "." or
char == ":" or
char == ";" or
+ char == "," or
char == "#" then
return true
end
break
end
+ if i == s and isnumber(char) == true then
+ break
+ end
+
table.insert(buf, char)
end
local function readint(line, s)
local len = #line
local buf = { }
+ local hex = false
for i = s, len do
local char = line:sub(i, i)
+
if isnumber(char) == false then
- break
+ if hex == false then
+ if char == "h" and (i - s) == 1 then
+ local prefix = line:sub(i - 1, i - 1)
+
+ if prefix ~= "0" then
+ perror("illegal token `" .. prefix .. "` next to number : " .. line)
+ end
+
+ hex = true
+ else
+ if char ~= "" and char ~= " " then
+ print("illegal sufix for number line : " .. line)
+ end
+ end
+ else
+ if char == "" or char == " " then
+ break
+ end
+
+ if char ~= "a" and char ~= "A" and char ~= "b" and char ~= "B" and
+ char ~= "c" and char ~= "C" and char ~= "d" and char ~= "D" and
+ char ~= "e" and char ~= "E" and char ~= "f" and char ~= "F" then
+ perror("illegal sufix `" .. char .. "` for hexadecimal " .. line)
+ end
+ end
end
table.insert(buf, char)
write_u16(TOKEN_SEMICOLON)
elseif char == "#" then
write_u16(TOKEN_HASH)
+ elseif char == "," then
+ write_u16(TOKEN_COMMA)
else
print("Unknown symbol : " .. char)
end
elseif isnumber(char) then
local sint = readint(line, i)
+ local ishex = false
+
+ if sint:sub(2, 2) == "h" then
+ ishex = true
+ end
+
local j = 1
write_u32(nline)
write_u32(column)
+ if ishex == true then
+ write_u16(TOKEN_HEXADECIMAL)
+ else
+ write_u16(TOKEN_INTEGER)
+ end
write_u16(#sint)
i = i + #sint
if id == "asm" then
write_u16(TOKEN_ASM)
write_u16(0)
+ elseif id == "hlt" then
+ write_u16(TOKEN_HLT)
+ write_u16(0)
+ elseif id == "ret" then
+ write_u16(TOKEN_RET)
+ write_u16(0)
+ elseif id == "cli" then
+ write_u16(TOKEN_CLI)
+ write_u16(0)
+ elseif id == "sti" then
+ write_u16(TOKEN_STI)
+ write_u16(0)
+ elseif id == "ah" then
+ write_u16(TOKEN_AH)
+ write_u16(0)
+ elseif id == "al" then
+ write_u16(TOKEN_AL)
+ write_u16(0)
+ elseif id == "bh" then
+ write_u16(TOKEN_BH)
+ write_u16(0)
+ elseif id == "bl" then
+ write_u16(TOKEN_BL)
+ write_u16(0)
+ elseif id == "ch" then
+ write_u16(TOKEN_CH)
+ write_u16(0)
+ elseif id == "cl" then
+ write_u16(TOKEN_CL)
+ write_u16(0)
+ elseif id == "dh" then
+ write_u16(TOKEN_DH)
+ write_u16(0)
+ elseif id == "dl" then
+ write_u16(TOKEN_DL)
+ write_u16(0)
+ elseif id == "mov" then
+ write_u16(TOKEN_MOV)
+ write_u16(0)
else
local j = 1
write_u16(TOKEN_ID)
src:close()
dst:close()
+
+print(progname .. ": " .. arg[1] .. " -> " .. arg[2])
blob - 11e1d810af892577140dd17861cc1755c5503e5a
blob + ce8ce69a13ac2aa9f4ce553f4fe23518d06d60e8
--- tools/6l
+++ tools/6l
progname = "6l"
if (arg[1] == nil) then
- print("usage: " .. progname .. " file")
+ print("usage: " .. progname .. " [file ...]")
os.exit(1)
end
+
+if arg[2] == nil then
+ arg[2] = "6." ..string.gsub(arg[1], "%.%w+$", "")
+end
+
+local function perror(msg)
+ print(progname .. ": error: " .. msg)
+ os.exit(1)
+end
+
+src = io.open(arg[1], "rb")
+
+if src == nil then
+ perror("failed to open " .. arg[1])
+end
+
+dst = io.open(arg[2], "wb")
+
+if dst == nil then
+ perror("failed to open " .. arg[2])
+end
+
+local function brshift(value, bit)
+ return math.floor(value / (2 ^ bit))
+end
+
+local function blshift(value, bit)
+ return value * (2 ^ bit)
+end
+
+local function bor(a, b)
+ local result = 0
+ local shift = 1
+
+ while a > 0 or b > 0 do
+ local r1 = a % 2
+ local r2 = b % 2
+
+ if r1 == 1 or r2 == 1 then
+ result = result + shift
+ end
+
+ a = math.floor(a / 2)
+ b = math.floor(b / 2)
+ shift = shift * 2
+ end
+
+ return result
+end
+
+--[[
+
+Token {
+ u32 Line;
+ u32 Column;
+ u16 Type;
+ u16 Length;
+}
+
+]]--
+
+local TOKEN_ASM = 0
+local TOKEN_LEFT_CURLY_BRACKET = 1
+local TOKEN_RIGHT_CURLY_BRACKET = 2
+local TOKEN_MULTIPLY = 3
+local TOKEN_DIVIDE = 4
+local TOKEN_SUBTRACT = 5
+local TOKEN_ADD = 6
+local TOKEN_LEFT_SQUARE_BRACKET = 7
+local TOKEN_RIGHT_SQUARE_BRACKET = 8
+local TOKEN_LEFT_PARANTHESIS = 9
+local TOKEN_RIGHT_PARANTHESIS = 10
+local TOKEN_QUESTION = 11
+local TOKEN_EXCLAMATION = 12
+local TOKEN_TILDA = 13
+local TOKEN_PERIOD = 14
+local TOKEN_COLUMN = 15
+local TOKEN_INTEGER = 16
+local TOKEN_ID = 17
+local TOKEN_STRING = 18
+local TOKEN_SEMICOLON = 19
+local TOKEN_HASH = 20
+local TOKEN_COMMA = 21
+local TOKEN_HLT = 22
+local TOKEN_RET = 23
+local TOKEN_CLI = 24
+local TOKEN_STI = 25
+local TOKEN_AH = 26
+local TOKEN_AL = 27
+local TOKEN_BH = 28
+local TOKEN_BL = 29
+local TOKEN_CL = 30
+local TOKEN_CH = 31
+local TOKEN_DL = 32
+local TOKEN_DH = 33
+local TOKEN_MOV = 34
+local TOKEN_HEXADECIMAL = 35
+
+local asm = {
+ hlt = 0xF4,
+ ret = 0xC3, -- Near return
+ cli = 0xFA,
+ sti = 0xFB,
+}
+
+local MODE_NONE = 0
+local MODE_ASM = 1
+
+function readtoken()
+ local header = src:read(12)
+
+ if header == nil then
+ return nil
+ end
+
+ local b = { string.byte(header, 1, 12) }
+
+ local line = b[4] + blshift(b[3], 8) + blshift(b[2], 16) + blshift(b[1], 24)
+ local col = b[8] + blshift(b[7], 8) + blshift(b[6], 16) + blshift(b[5], 24)
+ local type = b[10] + blshift(b[9], 8)
+ local length = b[12] + blshift(b[11], 8)
+ local raw = src:read(length)
+
+ return { column = col, line = line, type = type, length = length, raw = raw }
+end
+
+function hexval(hex)
+ local dig = hex:sub(3)
+ local len = #dig
+ local result = 0
+
+ for i = 1,len do
+ local d = dig:sub(i, i)
+
+ if d:lower() == "a" then
+ d = 10
+ elseif d:lower() == "b" then
+ d = 11
+ elseif d:lower() == "c" then
+ d = 12
+ elseif d:lower() == "d" then
+ d = 13
+ elseif d:lower() == "e" then
+ d = 14
+ elseif d:lower() == "f" then
+ d = 15
+ end
+
+ result = result + d * (16 ^ (len - i))
+ end
+
+ return result
+end
+
+local mode = MODE_NONE
+local brace_depth = 0
+local begin = src:seek("cur")
+
+while true do
+ local token = readtoken()
+ if token == nil then
+ break
+ end
+
+ -- Syntax check
+ if token.type == TOKEN_ASM then
+ if mode == MODE_ASM then
+ perror("error: nested asm attempt at line " .. token.line .. " column " .. token.column)
+ break
+ end
+
+ local next = readtoken()
+ if next == nil or next.type ~= TOKEN_LEFT_CURLY_BRACKET then
+ perror("error: missing '{' after asm at line " .. token.line .. " column " .. token.column)
+ break
+ end
+
+ mode = MODE_ASM
+ elseif token.type == TOKEN_HLT then
+ if mode ~= MODE_ASM then
+ perror("error: hlt instruction outside asm block at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local next = readtoken()
+
+ if next ~= nil and next.line == token.line then
+ perror("error: illegal token next to hlt on line " .. token.line .. " column " ..
+ token.column)
+ end
+ elseif token.type == TOKEN_RET then
+ if mode ~= MODE_ASM then
+ perror("error: ret instruction out of asm block at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local next = readtoken()
+ if next ~= nil and next.line == token.line then
+ perror("error: illegal token after ret on line " .. token.line " .. column " ..
+ token.column)
+ end
+ elseif token.type == TOKEN_CLI then
+ if mode ~= MODE_ASM then
+ perror("error: cli instruction out of asm block at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local next = readtoken()
+ if next ~= nil and next.line == token.line then
+ perror("error: illegal token after cli on line " .. token.line " .. column " ..
+ token.column)
+ end
+ elseif token.type == TOKEN_STI then
+ if mode ~= MODE_ASM then
+ perror("error: sti instruction out of asm block at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local next = readtoken()
+ if next ~= nil and next.line == token.line then
+ perror("error: illegal token after sti on line " .. token.line " .. column " ..
+ token.column)
+ end
+
+ elseif token.type == TOKEN_MOV then
+ if mode ~= MODE_ASM then
+ perror("error: sti instruction out of asm block at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local op1 = readtoken()
+
+ if op1.type ~= TOKEN_AL and op1.type ~= TOKEN_AH and op1.type ~= TOKEN_BL and
+ op1.type ~= TOKEN_BH and op1.type ~= TOKEN_CH and
+ op1.type ~= TOKEN_CL and op1.type ~= TOKEN_DH and
+ op1.type ~= TOKEN_DL then
+ perror("illegal first operand for mov at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local comma = readtoken()
+
+ if comma.type ~= TOKEN_COMMA then
+ perror("missing comma next to first operand line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ local op2 = readtoken()
+
+ if op2.type ~= TOKEN_AL and op2.type ~= TOKEN_AH and op2.type ~= TOKEN_BL and
+ op2.type ~= TOKEN_BH and op2.type ~= TOKEN_CH and
+ op2.type ~= TOKEN_CL and op2.type ~= TOKEN_DH and
+ op2.type ~= TOKEN_DL and op2.type ~= TOKEN_HEXADECIMAL then
+ perror("illegal second operand for mov at line " .. token.line .. " column " ..
+ token.column)
+ end
+
+ -- Checking if hex value is to high: mov r8, imm8
+ if op2.type == TOKEN_HEXADECIMAL and
+ (op1.type == TOKEN_AH or op1.type == TOKEN_AL or
+ op1.type == TOKEN_BH or op1.type == TOKEN_BL or
+ op1.type == TOKEN_CH or op1.type == TOKEN_CL or
+ op1.type == TOKEN_DH or op1.type == TOKEN_DL) then
+ if hexval(op2.raw) > 255 then
+ perror("hexvalue too high at line " .. token.line .. " column " .. token.column)
+ end
+ end
+ end
+end
+
+src:seek("set", begin)
+
+while true do
+ local token = readtoken()
+ if token == nil then
+ break
+ end
+
+ if token.type == TOKEN_HLT then
+ dst:write(string.char(asm.hlt))
+ elseif token.type == TOKEN_RET then
+ dst:write(string.char(asm.ret))
+ elseif token.type == TOKEN_CLI then
+ dst:write(string.char(asm.cli))
+ elseif token.type == TOKEN_STI then
+ dst:write(string.char(asm.sti))
+ elseif token.type == TOKEN_MOV then
+ local op1 = readtoken()
+ readtoken() -- Comma
+ local op2 = readtoken()
+
+ if op1.type == TOKEN_AL then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("000", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_AH then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("100", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_BL then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("011", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_BH then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("111", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_CL then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("001", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_CH then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("101", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_DL then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("010", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ elseif op1.type == TOKEN_DH then
+ if op2.type == TOKEN_HEXADECIMAL then
+ local opcode = { hexval("0hB0") + tonumber("110", 2), hexval(op2.raw) }
+
+ dst:write(string.char(opcode[1]))
+ dst:write(string.char(opcode[2]))
+ end
+ end
+ end
+end
+
+src:close()
+dst:close()
+print(arg[1] .. " -> " .. arg[2])
blob - 41132f6b89059a67428a66b152a26ab7cf840a38
blob + 17dc1369b1522cc6139fcb7b47f9086f35c4d8bb
--- tools/boot.c
+++ tools/boot.c
-import libc;
-
asm {
_start:
- hlt
+ ret
}
-
-void main()
-{
- u64 var = 22;
-}