kio++
This commit is contained in:
parent
14fdfdce70
commit
e44d6177a0
2
.buildactions/00_setup.lua
Normal file
2
.buildactions/00_setup.lua
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
os.execute("mkdir -p build")
|
||||||
|
os.execute("rm -rf build/*")
|
211
.buildactions/01_velx.lua
Normal file
211
.buildactions/01_velx.lua
Normal file
@ -0,0 +1,211 @@
|
|||||||
|
-- VELX builder
|
||||||
|
|
||||||
|
--[[----------------------------------------------------------------------------
|
||||||
|
LZSS - encoder / decoder
|
||||||
|
This is free and unencumbered software released into the public domain.
|
||||||
|
Anyone is free to copy, modify, publish, use, compile, sell, or
|
||||||
|
distribute this software, either in source code form or as a compiled
|
||||||
|
binary, for any purpose, commercial or non-commercial, and by any
|
||||||
|
means.
|
||||||
|
In jurisdictions that recognize copyright laws, the author or authors
|
||||||
|
of this software dedicate any and all copyright interest in the
|
||||||
|
software to the public domain. We make this dedication for the benefit
|
||||||
|
of the public at large and to the detriment of our heirs and
|
||||||
|
successors. We intend this dedication to be an overt act of
|
||||||
|
relinquishment in perpetuity of all present and future rights to this
|
||||||
|
software under copyright law.
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||||
|
IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||||
|
OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||||
|
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
For more information, please refer to <http://unlicense.org/>
|
||||||
|
--]]----------------------------------------------------------------------------
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
local M = {}
|
||||||
|
local string, table = string, table
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
local POS_BITS = 12
|
||||||
|
local LEN_BITS = 16 - POS_BITS
|
||||||
|
local POS_SIZE = 1 << POS_BITS
|
||||||
|
local LEN_SIZE = 1 << LEN_BITS
|
||||||
|
local LEN_MIN = 3
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
function M.compress(input)
|
||||||
|
local offset, output = 1, {}
|
||||||
|
local window = ''
|
||||||
|
|
||||||
|
local function search()
|
||||||
|
for i = LEN_SIZE + LEN_MIN - 1, LEN_MIN, -1 do
|
||||||
|
local str = string.sub(input, offset, offset + i - 1)
|
||||||
|
local pos = string.find(window, str, 1, true)
|
||||||
|
if pos then
|
||||||
|
return pos, str
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
while offset <= #input do
|
||||||
|
local flags, buffer = 0, {}
|
||||||
|
|
||||||
|
for i = 0, 7 do
|
||||||
|
if offset <= #input then
|
||||||
|
local pos, str = search()
|
||||||
|
if pos and #str >= LEN_MIN then
|
||||||
|
local tmp = ((pos - 1) << LEN_BITS) | (#str - LEN_MIN)
|
||||||
|
buffer[#buffer + 1] = string.pack('>I2', tmp)
|
||||||
|
else
|
||||||
|
flags = flags | (1 << i)
|
||||||
|
str = string.sub(input, offset, offset)
|
||||||
|
buffer[#buffer + 1] = str
|
||||||
|
end
|
||||||
|
window = string.sub(window .. str, -POS_SIZE)
|
||||||
|
offset = offset + #str
|
||||||
|
else
|
||||||
|
break
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
if #buffer > 0 then
|
||||||
|
output[#output + 1] = string.char(flags)
|
||||||
|
output[#output + 1] = table.concat(buffer)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
return table.concat(output)
|
||||||
|
end
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
function M.decompress(input)
|
||||||
|
local offset, output = 1, {}
|
||||||
|
local window = ''
|
||||||
|
|
||||||
|
while offset <= #input do
|
||||||
|
local flags = string.byte(input, offset)
|
||||||
|
offset = offset + 1
|
||||||
|
|
||||||
|
for i = 1, 8 do
|
||||||
|
local str = nil
|
||||||
|
if (flags & 1) ~= 0 then
|
||||||
|
if offset <= #input then
|
||||||
|
str = string.sub(input, offset, offset)
|
||||||
|
offset = offset + 1
|
||||||
|
end
|
||||||
|
else
|
||||||
|
if offset + 1 <= #input then
|
||||||
|
local tmp = string.unpack('>I2', input, offset)
|
||||||
|
offset = offset + 2
|
||||||
|
local pos = (tmp >> LEN_BITS) + 1
|
||||||
|
local len = (tmp & (LEN_SIZE - 1)) + LEN_MIN
|
||||||
|
str = string.sub(window, pos, pos + len - 1)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
flags = flags >> 1
|
||||||
|
if str then
|
||||||
|
output[#output + 1] = str
|
||||||
|
window = string.sub(window .. str, -POS_SIZE)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
return table.concat(output)
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
local function struct(tbl)
|
||||||
|
local pat = tbl.endian or "="
|
||||||
|
local args = {}
|
||||||
|
for i=1, #tbl do
|
||||||
|
local a, b = pairs(tbl[i])
|
||||||
|
local k, v = a(b)
|
||||||
|
args[i] = k
|
||||||
|
pat = pat .. v
|
||||||
|
end
|
||||||
|
return setmetatable({}, {__call=function(_, arg)
|
||||||
|
--checkArg(1, arg, "string", "table")
|
||||||
|
if (type(arg) == "string") then
|
||||||
|
local sval = {string.unpack(pat, arg)}
|
||||||
|
local rtn = {}
|
||||||
|
for i=1, #args do
|
||||||
|
rtn[args[i]] = sval[i]
|
||||||
|
end
|
||||||
|
return rtn, sval[#sval]
|
||||||
|
elseif (type(arg) == "table") then
|
||||||
|
local sval = {}
|
||||||
|
for i=1, #args do
|
||||||
|
sval[i] = arg[args[i]]
|
||||||
|
end
|
||||||
|
return string.pack(pat, unpack(sval))
|
||||||
|
end
|
||||||
|
end, __len=function()
|
||||||
|
return string.packsize(pat)
|
||||||
|
end})
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
local velx_spec = struct {
|
||||||
|
endian = "<",
|
||||||
|
{magic="c5"},
|
||||||
|
{fver="B"},
|
||||||
|
{compression="B"},
|
||||||
|
{lver="B"},
|
||||||
|
{os="B"},
|
||||||
|
{arctype="c4"},
|
||||||
|
{psize="I3"},
|
||||||
|
{lsize="I3"},
|
||||||
|
{ssize="I3"},
|
||||||
|
{rsize="I4"}
|
||||||
|
}
|
||||||
|
|
||||||
|
local function velx_multistep(path, arcpath, args, steps)
|
||||||
|
local shell_args = ""
|
||||||
|
for k, v in pairs(args) do
|
||||||
|
shell_args = shell_args .. k .. "=\"".. v .."\" "
|
||||||
|
end
|
||||||
|
steps.precomp()
|
||||||
|
local h = io.popen(shell_args.."luacomp "..path, "r")
|
||||||
|
local prog = h:read("*a")
|
||||||
|
h:close()
|
||||||
|
prog = steps.postcomp(prog)
|
||||||
|
steps.prearc()
|
||||||
|
local arc = ""
|
||||||
|
if arcpath then
|
||||||
|
h = io.popen("find "..arcpath.." -depth | tsar -o", "r")
|
||||||
|
arc = h:read("*a")
|
||||||
|
h:close()
|
||||||
|
steps.postarc()
|
||||||
|
end
|
||||||
|
if (not args.noz) then
|
||||||
|
steps.prez()
|
||||||
|
prog = M.compress(prog)
|
||||||
|
steps.postz()
|
||||||
|
end
|
||||||
|
local header = velx_spec({
|
||||||
|
magic = "\27VelX",
|
||||||
|
compression = (args.noz and 0) or 1,
|
||||||
|
lver = 0x53,
|
||||||
|
fver = 1,
|
||||||
|
os = 0x7F,
|
||||||
|
psize = #prog,
|
||||||
|
lsize=0,
|
||||||
|
ssize=0,
|
||||||
|
rsize=#arc,
|
||||||
|
arctype=(arcpath and "tsar") or ""
|
||||||
|
})
|
||||||
|
return header .. prog .. arc
|
||||||
|
end
|
||||||
|
|
||||||
|
local function velx(path, arcpath, args)
|
||||||
|
return velx_multistep(path, arcpath, args, {
|
||||||
|
precomp = function()end,
|
||||||
|
postcomp = function(prog) return prog end,
|
||||||
|
prearc = function()end,
|
||||||
|
postarc = function()end,
|
||||||
|
prez = function()end,
|
||||||
|
postz = function()end,
|
||||||
|
})
|
||||||
|
end
|
50
.buildactions/11_kernel.lua
Normal file
50
.buildactions/11_kernel.lua
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
local TSUKI_RELEASE = "0.0.1"
|
||||||
|
local tz = os.date("%z")
|
||||||
|
tz = tz:sub(1, 3)..":"..tz:sub(4)
|
||||||
|
local TSUKI_VERSION = "Lua 5.3 "..os.date("%Y-%m-%dT%H:%M:%S")..tz
|
||||||
|
local TSUKI_TARGET = os.getenv("TSUKI_TARGET") or "OC"
|
||||||
|
|
||||||
|
function actions.kernel(dbg)
|
||||||
|
os.execute("mkdir -p build/kernel")
|
||||||
|
print("Compiling kernel...")
|
||||||
|
local h = io.open("build/kernel/tkrnl.velx", "wb")
|
||||||
|
h:write(velx_multistep("ksrc/init.lua", ".doc", {
|
||||||
|
TSUKI_RELEASE = TSUKI_RELEASE,
|
||||||
|
TSUKI_VERSION = TSUKI_VERSION,
|
||||||
|
TSUKI_TARGET = TSUKI_TARGET,
|
||||||
|
PRINT_DMESG_LEVEL = ((dbg and 0) or 1)
|
||||||
|
}, {
|
||||||
|
precomp = function()
|
||||||
|
print("Compiling kernel...")
|
||||||
|
end,
|
||||||
|
postcomp = function(krnl)
|
||||||
|
os.execute("mkdir .doc")
|
||||||
|
local h = io.open("build/kernel/debug.lua", "w")
|
||||||
|
h:write(krnl)
|
||||||
|
h:close()
|
||||||
|
print("Generating docs and stripping comments...")
|
||||||
|
h = io.popen("lua utils/gendocs.lua .doc 2>.ktmp", "w")
|
||||||
|
h:write(krnl)
|
||||||
|
h:close()
|
||||||
|
h = io.open(".ktmp", "rb")
|
||||||
|
local data = h:read("*a")
|
||||||
|
h:close()
|
||||||
|
os.execute("rm -rf .ktmp")
|
||||||
|
return data
|
||||||
|
end,
|
||||||
|
prearc = function()
|
||||||
|
print("Storing docs...")
|
||||||
|
end,
|
||||||
|
postarc = function()
|
||||||
|
os.execute("rm -rf .doc")
|
||||||
|
end,
|
||||||
|
prez = function()
|
||||||
|
print("Compressing kernel...")
|
||||||
|
end,
|
||||||
|
postz = function()
|
||||||
|
print("Writing kernel out...")
|
||||||
|
end
|
||||||
|
}))
|
||||||
|
end
|
||||||
|
|
||||||
|
actions[#actions+1] = "kernel"
|
7
.buildactions/20_crescent.lua
Normal file
7
.buildactions/20_crescent.lua
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
function actions.crescent()
|
||||||
|
os.execute("mkdir -p build/crescent")
|
||||||
|
os.execute("cd extras; lua ../utils/mkvelx.lua crescent/init.lua ../build/crescent/boot.velx")
|
||||||
|
os.execute("cp extras/crescent/bootvelxloader.lua build/crescent/init.lua")
|
||||||
|
end
|
||||||
|
|
||||||
|
actions[#actions+1] = "crescent"
|
7
.buildactions/30_velxboot.lua
Normal file
7
.buildactions/30_velxboot.lua
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
function actions.velxboot()
|
||||||
|
os.execute("mkdir -p build/velxboot")
|
||||||
|
os.execute("cd extras; luacomp velxboot/init.lua -O ../build/velxboot/bios.lua")
|
||||||
|
os.execute("cd extras; luacomp velxboot/flashvelxboot.lua -O ../build/velxboot/flashvelxboot.lua")
|
||||||
|
end
|
||||||
|
|
||||||
|
actions[#actions+1] = "velxboot"
|
37
.buildactions/40_coreutils.lua
Normal file
37
.buildactions/40_coreutils.lua
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
do
|
||||||
|
--local coreutils = {}
|
||||||
|
--local function add_coreutil(name, outfolder, args)
|
||||||
|
-- args = args or {}
|
||||||
|
-- if not os.execute("[[ -d build/coreutils/"..outfolder.." ]]") then
|
||||||
|
-- os.execute("mkdir -p build/coreutils/"..outfolder)
|
||||||
|
-- end
|
||||||
|
-- actions["coreutil_"..name] = function()
|
||||||
|
-- local data = velx("coreutils/"..name..".lua", nil, args)
|
||||||
|
-- local h = io.open("build/coreutils/"..outfolder.."/"..name..".velx", "w")
|
||||||
|
-- h:write(data)
|
||||||
|
-- h:close()
|
||||||
|
-- end
|
||||||
|
-- coreutils[#coreutils+1] = name
|
||||||
|
--end
|
||||||
|
|
||||||
|
--add_coreutil("init", "sbin")
|
||||||
|
--add_coreutil("shutdown", "sbin")
|
||||||
|
--add_coreutil("sh", "sbin")
|
||||||
|
--add_coreutil("uname", "sbin")
|
||||||
|
|
||||||
|
--function actions.coreutils()
|
||||||
|
-- for i=1, #coreutils do
|
||||||
|
-- actions["coreutil_"..coreutils[i]]()
|
||||||
|
-- end
|
||||||
|
--end
|
||||||
|
local version = "0.1"
|
||||||
|
function actions.coreutils()
|
||||||
|
print("Building coreutils...")
|
||||||
|
os.execute("mkdir -p build/coreutils")
|
||||||
|
local sks = io.open("build/coreutils/sks.velx", "w")
|
||||||
|
sks:write(velx("coreutils/multicall.lua", false, {
|
||||||
|
SKS_COREUTILS_VERSION = version
|
||||||
|
}))
|
||||||
|
end
|
||||||
|
actions[#actions+1] = "coreutils"
|
||||||
|
end
|
5
.buildactions/fe_debug.lua
Normal file
5
.buildactions/fe_debug.lua
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
function actions.debug()
|
||||||
|
for i=1, #actions do
|
||||||
|
actions[actions[i]](true)
|
||||||
|
end
|
||||||
|
end
|
5
.buildactions/ff_clean.lua
Normal file
5
.buildactions/ff_clean.lua
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
function actions.clean()
|
||||||
|
print("Cleaning up...")
|
||||||
|
--os.execute("rm -rf .docs")
|
||||||
|
--os.execute("rm -rf .ktmp")
|
||||||
|
end
|
235
build.lua
235
build.lua
@ -1,232 +1,21 @@
|
|||||||
os.execute("mkdir -p build")
|
|
||||||
os.execute("rm -rf build/*")
|
|
||||||
|
|
||||||
--[[----------------------------------------------------------------------------
|
|
||||||
LZSS - encoder / decoder
|
|
||||||
This is free and unencumbered software released into the public domain.
|
|
||||||
Anyone is free to copy, modify, publish, use, compile, sell, or
|
|
||||||
distribute this software, either in source code form or as a compiled
|
|
||||||
binary, for any purpose, commercial or non-commercial, and by any
|
|
||||||
means.
|
|
||||||
In jurisdictions that recognize copyright laws, the author or authors
|
|
||||||
of this software dedicate any and all copyright interest in the
|
|
||||||
software to the public domain. We make this dedication for the benefit
|
|
||||||
of the public at large and to the detriment of our heirs and
|
|
||||||
successors. We intend this dedication to be an overt act of
|
|
||||||
relinquishment in perpetuity of all present and future rights to this
|
|
||||||
software under copyright law.
|
|
||||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
||||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
||||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
|
||||||
IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
|
||||||
OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
|
||||||
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
|
||||||
OTHER DEALINGS IN THE SOFTWARE.
|
|
||||||
For more information, please refer to <http://unlicense.org/>
|
|
||||||
--]]----------------------------------------------------------------------------
|
|
||||||
--------------------------------------------------------------------------------
|
|
||||||
local M = {}
|
|
||||||
local string, table = string, table
|
|
||||||
|
|
||||||
--------------------------------------------------------------------------------
|
|
||||||
local POS_BITS = 12
|
|
||||||
local LEN_BITS = 16 - POS_BITS
|
|
||||||
local POS_SIZE = 1 << POS_BITS
|
|
||||||
local LEN_SIZE = 1 << LEN_BITS
|
|
||||||
local LEN_MIN = 3
|
|
||||||
|
|
||||||
--------------------------------------------------------------------------------
|
|
||||||
function M.compress(input)
|
|
||||||
local offset, output = 1, {}
|
|
||||||
local window = ''
|
|
||||||
|
|
||||||
local function search()
|
|
||||||
for i = LEN_SIZE + LEN_MIN - 1, LEN_MIN, -1 do
|
|
||||||
local str = string.sub(input, offset, offset + i - 1)
|
|
||||||
local pos = string.find(window, str, 1, true)
|
|
||||||
if pos then
|
|
||||||
return pos, str
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
while offset <= #input do
|
|
||||||
local flags, buffer = 0, {}
|
|
||||||
|
|
||||||
for i = 0, 7 do
|
|
||||||
if offset <= #input then
|
|
||||||
local pos, str = search()
|
|
||||||
if pos and #str >= LEN_MIN then
|
|
||||||
local tmp = ((pos - 1) << LEN_BITS) | (#str - LEN_MIN)
|
|
||||||
buffer[#buffer + 1] = string.pack('>I2', tmp)
|
|
||||||
else
|
|
||||||
flags = flags | (1 << i)
|
|
||||||
str = string.sub(input, offset, offset)
|
|
||||||
buffer[#buffer + 1] = str
|
|
||||||
end
|
|
||||||
window = string.sub(window .. str, -POS_SIZE)
|
|
||||||
offset = offset + #str
|
|
||||||
else
|
|
||||||
break
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
if #buffer > 0 then
|
|
||||||
output[#output + 1] = string.char(flags)
|
|
||||||
output[#output + 1] = table.concat(buffer)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
return table.concat(output)
|
|
||||||
end
|
|
||||||
|
|
||||||
--------------------------------------------------------------------------------
|
|
||||||
function M.decompress(input)
|
|
||||||
local offset, output = 1, {}
|
|
||||||
local window = ''
|
|
||||||
|
|
||||||
while offset <= #input do
|
|
||||||
local flags = string.byte(input, offset)
|
|
||||||
offset = offset + 1
|
|
||||||
|
|
||||||
for i = 1, 8 do
|
|
||||||
local str = nil
|
|
||||||
if (flags & 1) ~= 0 then
|
|
||||||
if offset <= #input then
|
|
||||||
str = string.sub(input, offset, offset)
|
|
||||||
offset = offset + 1
|
|
||||||
end
|
|
||||||
else
|
|
||||||
if offset + 1 <= #input then
|
|
||||||
local tmp = string.unpack('>I2', input, offset)
|
|
||||||
offset = offset + 2
|
|
||||||
local pos = (tmp >> LEN_BITS) + 1
|
|
||||||
local len = (tmp & (LEN_SIZE - 1)) + LEN_MIN
|
|
||||||
str = string.sub(window, pos, pos + len - 1)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
flags = flags >> 1
|
|
||||||
if str then
|
|
||||||
output[#output + 1] = str
|
|
||||||
window = string.sub(window .. str, -POS_SIZE)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
return table.concat(output)
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
local function struct(tbl)
|
|
||||||
local pat = tbl.endian or "="
|
|
||||||
local args = {}
|
|
||||||
for i=1, #tbl do
|
|
||||||
local a, b = pairs(tbl[i])
|
|
||||||
local k, v = a(b)
|
|
||||||
args[i] = k
|
|
||||||
pat = pat .. v
|
|
||||||
end
|
|
||||||
return setmetatable({}, {__call=function(_, arg)
|
|
||||||
--checkArg(1, arg, "string", "table")
|
|
||||||
if (type(arg) == "string") then
|
|
||||||
local sval = {string.unpack(pat, arg)}
|
|
||||||
local rtn = {}
|
|
||||||
for i=1, #args do
|
|
||||||
rtn[args[i]] = sval[i]
|
|
||||||
end
|
|
||||||
return rtn, sval[#sval]
|
|
||||||
elseif (type(arg) == "table") then
|
|
||||||
local sval = {}
|
|
||||||
for i=1, #args do
|
|
||||||
sval[i] = arg[args[i]]
|
|
||||||
end
|
|
||||||
return string.pack(pat, unpack(sval))
|
|
||||||
end
|
|
||||||
end, __len=function()
|
|
||||||
return string.packsize(pat)
|
|
||||||
end})
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
local velx_spec = struct {
|
|
||||||
endian = "<",
|
|
||||||
{magic="c5"},
|
|
||||||
{fver="B"},
|
|
||||||
{compression="B"},
|
|
||||||
{lver="B"},
|
|
||||||
{os="B"},
|
|
||||||
{arctype="c4"},
|
|
||||||
{psize="I3"},
|
|
||||||
{lsize="I3"},
|
|
||||||
{ssize="I3"},
|
|
||||||
{rsize="I4"}
|
|
||||||
}
|
|
||||||
local actions = {}
|
local actions = {}
|
||||||
|
|
||||||
function actions.kernel()
|
@[[local h = io.popen("ls .buildactions", "r")
|
||||||
-- This builds Tsuki into a VELX executable.
|
for line in h:lines() do]]
|
||||||
os.execute("mkdir -p build/kernel")
|
--#include @[{".buildactions/"..line}]
|
||||||
print("Compiling kernel...")
|
@[[end]]
|
||||||
local h = io.popen("luacomp ksrc/init.lua", "r")
|
|
||||||
local krnl = h:read("*a")
|
|
||||||
h:close()
|
|
||||||
os.execute("luacomp ksrc/init.lua -O build/kernel/debug.lua 2>/dev/null")
|
|
||||||
print("Generating docs and stripping comments...")
|
|
||||||
os.execute("mkdir .docs")
|
|
||||||
h = io.popen("lua utils/gendocs.lua .docs 2>.ktmp", "w")
|
|
||||||
h:write(krnl)
|
|
||||||
h:close()
|
|
||||||
h = io.popen("find .docs -depth | tsar -o", "r")
|
|
||||||
local arc = h:read("*a")
|
|
||||||
h:close()
|
|
||||||
h = io.open(".ktmp", "rb")
|
|
||||||
local data = h:read("*a")
|
|
||||||
h:close()
|
|
||||||
print("Compressing kernel...")
|
|
||||||
data = M.compress(data)
|
|
||||||
print("Writing out tkrnl.velx...")
|
|
||||||
local h = io.open("build/kernel/tkrnl.velx", "wb")
|
|
||||||
local header = velx_spec({
|
|
||||||
magic = "\27VelX",
|
|
||||||
compression = 1,
|
|
||||||
lver = 0x53,
|
|
||||||
fver = 1,
|
|
||||||
os = 0x7F,
|
|
||||||
psize = #data,
|
|
||||||
lsize=0,
|
|
||||||
ssize=0,
|
|
||||||
rsize=#arc,
|
|
||||||
arctype="tsar"
|
|
||||||
})
|
|
||||||
h:write(header)
|
|
||||||
h:write(data)
|
|
||||||
h:write(arc)
|
|
||||||
h:close()
|
|
||||||
end
|
|
||||||
|
|
||||||
function actions.crescent()
|
--[[function actions.debug()
|
||||||
os.execute("mkdir -p build/crescent")
|
actions.kernel(true)
|
||||||
os.execute("cd extras; lua ../utils/mkvelx.lua crescent/init.lua ../build/crescent/boot.velx")
|
|
||||||
os.execute("cp extras/crescent/bootvelxloader.lua build/crescent/init.lua")
|
|
||||||
end
|
|
||||||
|
|
||||||
function actions.velxboot()
|
|
||||||
os.execute("mkdir -p build/velxboot")
|
|
||||||
os.execute("cd extras; luacomp velxboot/init.lua -O ../build/velxboot/bios.lua")
|
|
||||||
os.execute("cd extras; luacomp velxboot/flashvelxboot.lua -O ../build/velxboot/flashvelxboot.lua")
|
|
||||||
end
|
|
||||||
|
|
||||||
function actions.clean()
|
|
||||||
print("Cleaning up...")
|
|
||||||
os.execute("rm -rf .docs")
|
|
||||||
os.execute("rm -rf .ktmp")
|
|
||||||
end
|
|
||||||
|
|
||||||
function actions.all()
|
|
||||||
actions.kernel()
|
|
||||||
actions.crescent()
|
actions.crescent()
|
||||||
actions.velxboot()
|
actions.velxboot()
|
||||||
actions.clean()
|
actions.clean()
|
||||||
|
end]]
|
||||||
|
|
||||||
|
function actions.all()
|
||||||
|
for i=1, #actions do
|
||||||
|
actions[actions[i]]()
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if not arg[1] then
|
if not arg[1] then
|
||||||
|
2
build.sh
Executable file
2
build.sh
Executable file
@ -0,0 +1,2 @@
|
|||||||
|
#!/usr/bin/env sh
|
||||||
|
luacomp build.lua 2>/dev/null | lua - "$@"
|
57
coreutils/init.lua
Normal file
57
coreutils/init.lua
Normal file
@ -0,0 +1,57 @@
|
|||||||
|
local kargs = ...
|
||||||
|
local kio = kernel.kmode_run("return kio")
|
||||||
|
local tty = kernel.kmode_run("return tty")
|
||||||
|
local exec = kernel.kmode_run("return exec")
|
||||||
|
local thd = require("thread")
|
||||||
|
local fs = require("filesystem")
|
||||||
|
local security = require("security")
|
||||||
|
|
||||||
|
kernel.dmesg(kernel.loglevel.INFO, "ksysinit started")
|
||||||
|
local function run_hooks(hook, args)
|
||||||
|
local hooks = fs.list("/etc/ksysinit/"..hook)
|
||||||
|
for i=1, #hooks do
|
||||||
|
local path = fs.resolve("/etc/ksysinit/"..hook.."/"..hooks[i])
|
||||||
|
local stat = fs.stat(path)
|
||||||
|
if (stat.mode == "file" and stat.uid == 0 and stat.gid == 0 and mode & 2 == 0) then
|
||||||
|
local f, err = loadfile(path)
|
||||||
|
if not f then
|
||||||
|
kernel.dmesg(kernel.loglevel.WARNING, "Failed to load startup hook `"..hooks[i].."': "..err)
|
||||||
|
goto continue
|
||||||
|
end
|
||||||
|
xpcall(function()
|
||||||
|
f(table.unpack(args))
|
||||||
|
end, function(err)
|
||||||
|
kernel.dmesg(kernel.loglevel.ERROR, "Error in startup hook `"..hooks[i].."': "..debug.traceback(err))
|
||||||
|
end)
|
||||||
|
end
|
||||||
|
::continue::
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
kernel.dmesg(kernel.loglevel.INFO, "running startup hooks")
|
||||||
|
run_hooks("startup", {})
|
||||||
|
|
||||||
|
kernel.dmesg(kernel.loglevel.INFO, "starting ttys")
|
||||||
|
for i=1, tonumber(kargs["tty.count"]) or 1 do
|
||||||
|
local pty = tty.get(i)
|
||||||
|
exec.loadfile("/sbin/login.velx", true, {
|
||||||
|
uid = 0,
|
||||||
|
gid = 0,
|
||||||
|
tty = pty
|
||||||
|
})
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Now we wait for shutdown or other things
|
||||||
|
while true do
|
||||||
|
local siginfo = kernel.sig_pull()
|
||||||
|
if siginfo.type == "shutdown" then
|
||||||
|
run_hooks("shutdown", {})
|
||||||
|
kernel.kmode_run([[computer.shutdown()]])
|
||||||
|
elseif siginfo.type == "reboot" then
|
||||||
|
run_hooks("shutdown", {})
|
||||||
|
kernel.kmode_run([[computer.shutdown(true)]])
|
||||||
|
elseif siginfo.type == "ipc" and siginfo.message[1] == "svcrun" and security.hasperm("svc", siginfo.uid, siginfo.gid) then
|
||||||
|
table.pack(table.unpack(siginfo.message, 4))
|
||||||
|
run_hooks("services/"..siginfo.message[2].."/"..siginfo.message[3], table.pack(table.unpack(siginfo.message, 4)))
|
||||||
|
end
|
||||||
|
end
|
45
coreutils/multicall.lua
Normal file
45
coreutils/multicall.lua
Normal file
@ -0,0 +1,45 @@
|
|||||||
|
local calls = {}
|
||||||
|
|
||||||
|
local function version_info()
|
||||||
|
print("SKS Coreutils version $[{SKS_COREUTILS_VERSION}]")
|
||||||
|
end
|
||||||
|
|
||||||
|
@[[function add_util(name)]]
|
||||||
|
calls["@[{name}]"] = function(...)
|
||||||
|
--#include @[{"coreutils/"..name..".lua"}]
|
||||||
|
end
|
||||||
|
@[[end]]
|
||||||
|
|
||||||
|
@[[
|
||||||
|
add_util("init")
|
||||||
|
add_util("reboot")
|
||||||
|
add_util("sh")
|
||||||
|
add_util("shutdown")
|
||||||
|
add_util("svc-ctl")
|
||||||
|
add_util("uname")
|
||||||
|
]]
|
||||||
|
|
||||||
|
calls.sks = function(prog, ...)
|
||||||
|
if not prog then
|
||||||
|
version_info()
|
||||||
|
print("SKS Coreutils multicall binary.\n")
|
||||||
|
print("Calls:")
|
||||||
|
local t = {}
|
||||||
|
for k, v in pairs(calls) do
|
||||||
|
t[#t+1] = k
|
||||||
|
end
|
||||||
|
print(table.concat(t, " "))
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
return calls[prog](...)
|
||||||
|
end
|
||||||
|
|
||||||
|
setmetatable(calls, {__index=function(_, i)
|
||||||
|
return function()
|
||||||
|
io.stderr:write("call "..i.." not found. run `sks' without args for list of calls.\n")
|
||||||
|
end
|
||||||
|
end})
|
||||||
|
|
||||||
|
local call = os.getenv("_"):match("/(.+)%.[^%.]+")
|
||||||
|
|
||||||
|
return calls[call](...)
|
5
coreutils/reboot.lua
Normal file
5
coreutils/reboot.lua
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
if (kernel) then
|
||||||
|
kernel.sig_push {
|
||||||
|
sigtype = "shutdown"
|
||||||
|
}
|
||||||
|
end
|
0
coreutils/sh.lua
Normal file
0
coreutils/sh.lua
Normal file
10
coreutils/shutdown.lua
Normal file
10
coreutils/shutdown.lua
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
if (kernel) then
|
||||||
|
if (os.getenv("_"):match("reboot.velx")) then
|
||||||
|
kernel.sig_push {sigtype = "reboot"}
|
||||||
|
else
|
||||||
|
kernel.sig_push {sigtype = "shutdown"}
|
||||||
|
end
|
||||||
|
else
|
||||||
|
io.stderr:write("must be run as root\n")
|
||||||
|
os.exit(-1)
|
||||||
|
end
|
6
coreutils/svc-ctl.lua
Normal file
6
coreutils/svc-ctl.lua
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
if (kernel) then
|
||||||
|
--#include "coreutils/svc-ctl/init.lua"
|
||||||
|
else
|
||||||
|
io.stderr:write("must be run as root\n")
|
||||||
|
os.exit(-1)
|
||||||
|
end
|
26
coreutils/svc-ctl/init.lua
Normal file
26
coreutils/svc-ctl/init.lua
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
local args = {...}
|
||||||
|
local thread = require("thread")
|
||||||
|
local ipc = require("ipc")
|
||||||
|
local fs = require("filesystem")
|
||||||
|
|
||||||
|
if not args[1] then
|
||||||
|
local svcs = {}
|
||||||
|
for f in fs.list("/etc/ksysinit/services") do
|
||||||
|
svcs[#svcs+1] = f
|
||||||
|
end
|
||||||
|
print(table.concat(svcs, ", "))
|
||||||
|
return 0
|
||||||
|
elseif args[1] and not args[2] then
|
||||||
|
local svcs = {}
|
||||||
|
for f in fs.list("/etc/ksysinit/services/"..args[1]) do
|
||||||
|
svcs[#svcs+1] = f
|
||||||
|
end
|
||||||
|
print(table.concat(svcs, ", "))
|
||||||
|
return 0
|
||||||
|
elseif not fs.exists("/etc/ksysinit/services/"..args[1].."/"..args[2]) then
|
||||||
|
io.stderr:write("hook `"..args[2].."' not found for `"..args[1].."'\n")
|
||||||
|
return 1
|
||||||
|
else
|
||||||
|
local proc = thread.get("/sbin/init")
|
||||||
|
ipc.send(proc, "svcrun", args[1], args[2])
|
||||||
|
end
|
58
coreutils/uname.lua
Normal file
58
coreutils/uname.lua
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
local sharg = require("sh_arg")
|
||||||
|
local args = sharg({
|
||||||
|
name = "uname",
|
||||||
|
desc = [[Print certain system information. With no OPTION, same as -s]],
|
||||||
|
options = {
|
||||||
|
{"kernel-name", "s", "print the kernel name"},
|
||||||
|
{"nodename", "n", "print the network node hostname"},
|
||||||
|
{"kernel-release", "r", "print the kernel release"},
|
||||||
|
{"kernel-version", "v", "print the kernel release"},
|
||||||
|
{"machine", "m", "print the machine hardware name"},
|
||||||
|
{"operating-system", "o", "print the operating system"},
|
||||||
|
{"version", false, "output version information and exit"}
|
||||||
|
},
|
||||||
|
}, ...)
|
||||||
|
|
||||||
|
if (args.version) then
|
||||||
|
version_info()
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.a or args.all) then
|
||||||
|
args.s = true
|
||||||
|
args.r = true
|
||||||
|
args.v = true
|
||||||
|
args.n = true
|
||||||
|
args.m = true
|
||||||
|
args.o = true
|
||||||
|
end
|
||||||
|
|
||||||
|
if table.select("#", ...) == 0 then
|
||||||
|
args.s = true
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.s) then
|
||||||
|
io.stdout:write(_KINFO.name.." ")
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.n) then
|
||||||
|
io.stdout:write(os.getenv("HOSTNAME").." ")
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.r) then
|
||||||
|
io.stdout:write(_KINFO.release.." ")
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.v) then
|
||||||
|
io.stdout:write(_KINFO.version.." ")
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.m) then
|
||||||
|
io.stdout:write(_KINFO.machine.." ")
|
||||||
|
end
|
||||||
|
|
||||||
|
if (args.o) then
|
||||||
|
io.stdout:write("SKS/Tsuki ")
|
||||||
|
end
|
||||||
|
|
||||||
|
io.stdout:write("\n")
|
517
debug.lua
517
debug.lua
@ -1,15 +1,140 @@
|
|||||||
|
os.execute("mkdir -p build")
|
||||||
|
os.execute("rm -rf build/*")
|
||||||
|
|
||||||
function struct(tbl)
|
local actions = {}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
-- VELX builder
|
||||||
|
|
||||||
|
--[[----------------------------------------------------------------------------
|
||||||
|
LZSS - encoder / decoder
|
||||||
|
This is free and unencumbered software released into the public domain.
|
||||||
|
Anyone is free to copy, modify, publish, use, compile, sell, or
|
||||||
|
distribute this software, either in source code form or as a compiled
|
||||||
|
binary, for any purpose, commercial or non-commercial, and by any
|
||||||
|
means.
|
||||||
|
In jurisdictions that recognize copyright laws, the author or authors
|
||||||
|
of this software dedicate any and all copyright interest in the
|
||||||
|
software to the public domain. We make this dedication for the benefit
|
||||||
|
of the public at large and to the detriment of our heirs and
|
||||||
|
successors. We intend this dedication to be an overt act of
|
||||||
|
relinquishment in perpetuity of all present and future rights to this
|
||||||
|
software under copyright law.
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||||
|
IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||||
|
OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||||
|
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
For more information, please refer to <http://unlicense.org/>
|
||||||
|
--]]----------------------------------------------------------------------------
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
local M = {}
|
||||||
|
local string, table = string, table
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
local POS_BITS = 12
|
||||||
|
local LEN_BITS = 16 - POS_BITS
|
||||||
|
local POS_SIZE = 1 << POS_BITS
|
||||||
|
local LEN_SIZE = 1 << LEN_BITS
|
||||||
|
local LEN_MIN = 3
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
function M.compress(input)
|
||||||
|
local offset, output = 1, {}
|
||||||
|
local window = ''
|
||||||
|
|
||||||
|
local function search()
|
||||||
|
for i = LEN_SIZE + LEN_MIN - 1, LEN_MIN, -1 do
|
||||||
|
local str = string.sub(input, offset, offset + i - 1)
|
||||||
|
local pos = string.find(window, str, 1, true)
|
||||||
|
if pos then
|
||||||
|
return pos, str
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
while offset <= #input do
|
||||||
|
local flags, buffer = 0, {}
|
||||||
|
|
||||||
|
for i = 0, 7 do
|
||||||
|
if offset <= #input then
|
||||||
|
local pos, str = search()
|
||||||
|
if pos and #str >= LEN_MIN then
|
||||||
|
local tmp = ((pos - 1) << LEN_BITS) | (#str - LEN_MIN)
|
||||||
|
buffer[#buffer + 1] = string.pack('>I2', tmp)
|
||||||
|
else
|
||||||
|
flags = flags | (1 << i)
|
||||||
|
str = string.sub(input, offset, offset)
|
||||||
|
buffer[#buffer + 1] = str
|
||||||
|
end
|
||||||
|
window = string.sub(window .. str, -POS_SIZE)
|
||||||
|
offset = offset + #str
|
||||||
|
else
|
||||||
|
break
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
if #buffer > 0 then
|
||||||
|
output[#output + 1] = string.char(flags)
|
||||||
|
output[#output + 1] = table.concat(buffer)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
return table.concat(output)
|
||||||
|
end
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
function M.decompress(input)
|
||||||
|
local offset, output = 1, {}
|
||||||
|
local window = ''
|
||||||
|
|
||||||
|
while offset <= #input do
|
||||||
|
local flags = string.byte(input, offset)
|
||||||
|
offset = offset + 1
|
||||||
|
|
||||||
|
for i = 1, 8 do
|
||||||
|
local str = nil
|
||||||
|
if (flags & 1) ~= 0 then
|
||||||
|
if offset <= #input then
|
||||||
|
str = string.sub(input, offset, offset)
|
||||||
|
offset = offset + 1
|
||||||
|
end
|
||||||
|
else
|
||||||
|
if offset + 1 <= #input then
|
||||||
|
local tmp = string.unpack('>I2', input, offset)
|
||||||
|
offset = offset + 2
|
||||||
|
local pos = (tmp >> LEN_BITS) + 1
|
||||||
|
local len = (tmp & (LEN_SIZE - 1)) + LEN_MIN
|
||||||
|
str = string.sub(window, pos, pos + len - 1)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
flags = flags >> 1
|
||||||
|
if str then
|
||||||
|
output[#output + 1] = str
|
||||||
|
window = string.sub(window .. str, -POS_SIZE)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
return table.concat(output)
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
local function struct(tbl)
|
||||||
local pat = tbl.endian or "="
|
local pat = tbl.endian or "="
|
||||||
local args = {}
|
local args = {}
|
||||||
for i=1, do
|
for i=1, #tbl do
|
||||||
local a, b = pairs(tbl[i])
|
local a, b = pairs(tbl[i])
|
||||||
local k, v = a(b)
|
local k, v = a(b)
|
||||||
args[i] = k
|
args[i] = k
|
||||||
pat = pat .. v
|
pat = pat .. v
|
||||||
end
|
end
|
||||||
return setmetatable({}, {__call=function(_, arg)
|
return setmetatable({}, {__call=function(_, arg)
|
||||||
checkArg(1, arg, "string", "table")
|
--checkArg(1, arg, "string", "table")
|
||||||
if (type(arg) == "string") then
|
if (type(arg) == "string") then
|
||||||
local sval = {string.unpack(pat, arg)}
|
local sval = {string.unpack(pat, arg)}
|
||||||
local rtn = {}
|
local rtn = {}
|
||||||
@ -29,57 +154,6 @@ function struct(tbl)
|
|||||||
end})
|
end})
|
||||||
end
|
end
|
||||||
|
|
||||||
function string.trim(self)
|
|
||||||
return self:gsub("^%s+", ""):gsub("%s+$", "")
|
|
||||||
end
|
|
||||||
|
|
||||||
function string.explode(self, pat)
|
|
||||||
local t, ll
|
|
||||||
t={}
|
|
||||||
ll=0
|
|
||||||
if(#p == 1) then
|
|
||||||
return {p}
|
|
||||||
end
|
|
||||||
while true do
|
|
||||||
l = string.find(self, pat, ll, true) -- find the next d in the string
|
|
||||||
if l ~= nil then -- if "not not" found then..
|
|
||||||
table.insert(t, string.sub(self,ll,l-1)) -- Save it in our array.
|
|
||||||
ll = l + 1 -- save just after where we found it for searching next time.
|
|
||||||
else
|
|
||||||
table.insert(t, string.sub(self,ll)) -- Save what's left in our array.
|
|
||||||
break -- Break at end, as it should be, according to the lua manual.
|
|
||||||
end
|
|
||||||
end
|
|
||||||
return t
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
---@module security Security
|
|
||||||
local security = {}
|
|
||||||
|
|
||||||
---@func checkacl
|
|
||||||
---@arg permission string "The permission to check."
|
|
||||||
---@return boolean "True if the current process has this permission."
|
|
||||||
function security.checkacl(permission)
|
|
||||||
local perms = acl.get("group", thread.info().egid, {})
|
|
||||||
end
|
|
||||||
|
|
||||||
---@func getmode
|
|
||||||
---@return string "The current security mode."
|
|
||||||
function security.getmode()
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
function security.init()
|
|
||||||
klog("security", 1, "Security init started.")
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
local velx = (function()
|
|
||||||
|
|
||||||
|
|
||||||
local velx_spec = struct {
|
local velx_spec = struct {
|
||||||
endian = "<",
|
endian = "<",
|
||||||
@ -88,237 +162,150 @@ local velx_spec = struct {
|
|||||||
{compression="B"},
|
{compression="B"},
|
||||||
{lver="B"},
|
{lver="B"},
|
||||||
{os="B"},
|
{os="B"},
|
||||||
|
{arctype="c4"},
|
||||||
{psize="I3"},
|
{psize="I3"},
|
||||||
{lsize="I3"},
|
{lsize="I3"},
|
||||||
{ssize="I3"},
|
{ssize="I3"},
|
||||||
{rsize="I4"}
|
{rsize="I4"}
|
||||||
}
|
}
|
||||||
|
|
||||||
local velx = {}
|
local function velx_multistep(path, arcpath, args, steps)
|
||||||
|
local shell_args = ""
|
||||||
local exec = {}
|
for k, v in pairs(args) do
|
||||||
|
shell_args = shell_args .. k .. "=".. v .." "
|
||||||
function velx.identify(path)
|
end
|
||||||
local h = io.open(path, "rb")
|
steps.precomp()
|
||||||
local header = velx_spec(h:read(#velx_spec))
|
local h = io.popen(shell_args.."luacomp "..path, "r")
|
||||||
|
local prog = h:read("*a")
|
||||||
h:close()
|
h:close()
|
||||||
return header.magic == "\27VelX"
|
prog = steps.postcomp(prog)
|
||||||
end
|
steps.prearc()
|
||||||
|
h = io.popen("find .docs -depth | tsar -o", "r")
|
||||||
function velx.load(path)
|
local arc = h:read("*a")
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
function velx.verify(path)
|
|
||||||
local h = io.open(path, "rb")
|
|
||||||
local header = velx_spec(h:read(#velx_spec))
|
|
||||||
local code = h:read(header.psize)
|
|
||||||
h:seek("cur", lsize)
|
|
||||||
local sig = h:read(header.ssize)
|
|
||||||
h:close()
|
h:close()
|
||||||
return security.verify(code, sig)
|
steps.postarc()
|
||||||
|
if (not args.noz) then
|
||||||
|
steps.prez()
|
||||||
|
prog = M.compress(prog)
|
||||||
|
steps.postz()
|
||||||
|
end
|
||||||
|
local header = velx_spec({
|
||||||
|
magic = "\27VelX",
|
||||||
|
compression = (args.noz and 0 or) 1,
|
||||||
|
lver = 0x53,
|
||||||
|
fver = 1,
|
||||||
|
os = 0x7F,
|
||||||
|
psize = #prog,
|
||||||
|
lsize=0,
|
||||||
|
ssize=0,
|
||||||
|
rsize=#arc,
|
||||||
|
arctype="tsar"
|
||||||
|
})
|
||||||
|
return header .. prog .. arc
|
||||||
end
|
end
|
||||||
|
|
||||||
function exec:link()
|
local function velx(path, arcpath, args)
|
||||||
self.file:seek("set", #velx_spec+self.header.psize)
|
return velx_multistep(path, arcpath, args, {
|
||||||
local linkinfo = self.file:read(self.header.lsize)
|
precomp = function()end
|
||||||
local linker = {}
|
postcomp = function(prog) return prog end
|
||||||
local pos = 1
|
prearc = function()end
|
||||||
while true do
|
postarc = function()end
|
||||||
local size = string.unpack("<H", linkinfo:sub(pos))
|
prez = function()end
|
||||||
pos = pos + 2
|
postz = function()end
|
||||||
local name = linkinfo:sub(pos, pos+size-1)
|
})
|
||||||
pos = pos + size
|
|
||||||
size = string.unpack("<H", linkinfo:sub(pos))
|
|
||||||
pos = pos + 2
|
|
||||||
local library = linkinfo:sub(pos, pos+size-1)
|
|
||||||
pos = pos + size
|
|
||||||
if (name == "" or library == "") then
|
|
||||||
break
|
|
||||||
end
|
|
||||||
linker[#linker+1] = {name, library}
|
|
||||||
end
|
|
||||||
local linkscript = ""
|
|
||||||
for i=1, #linker do
|
|
||||||
linkscript = linkscript .. "local " .. linker[i][1] .. "=require(\"" .. linker[i][2] .. "\")\n"
|
|
||||||
end
|
|
||||||
self.code = linkscript .. self.code
|
|
||||||
return true
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function exec:load()
|
local TSUKI_RELEASE = "0.0.1"
|
||||||
self.file:seek("set", #velx_spec)
|
local tz = os.date("%z")
|
||||||
local code = self.file:read(self.header.psize)
|
tz = tz:sub(1, 3)..":"..tz:sub(4)
|
||||||
if (self.header.compression == 0) then
|
local TSUKI_VERSION = "Lua 5.3 "..os.date("%Y-%m-%dT%H:%M:%S")..tz
|
||||||
self.code = code
|
local TSUKI_TARGET = os.getenv("TSUKI_TARGET") or "OC"
|
||||||
elseif (self.header.compression == 1) then
|
|
||||||
self.code = lzss.decompress(self.code)
|
|
||||||
else
|
|
||||||
return nil, "invalid compression method"
|
|
||||||
end
|
|
||||||
return true
|
|
||||||
end
|
|
||||||
|
|
||||||
function exec:run(args, evar)
|
function actions.kernel(dbg)
|
||||||
system.load(self.code, args, system.getglobalenv({_ARCHIVE=self.arc}), system.getevars(evar))
|
os.execute("mkdir -p build/kernel")
|
||||||
end
|
print("Compiling kernel...")
|
||||||
|
local h = io.open("build/kernel/tkrnl.velx", "wb")
|
||||||
end)()
|
h:write(velx_multistep("ksrc/init.lua", ".docs", {
|
||||||
|
TSUKI_RELEASE = TSUKI_RELEASE,
|
||||||
local zlua = (function()
|
TSUKI_VERSION = TSUKI_VERSION,
|
||||||
|
TSUKI_TARGET = TSUKI_TARGET,
|
||||||
local zlua = {}
|
PRINT_DMESG_LEVEL = ((dbg and 0) or 1)
|
||||||
|
}, {
|
||||||
return {}
|
precomp = function()
|
||||||
end)
|
print("Compiling kernel...")
|
||||||
|
|
||||||
-- Executable loading process:
|
|
||||||
-- - Link
|
|
||||||
-- - Load
|
|
||||||
-- - Execute
|
|
||||||
|
|
||||||
if ()
|
|
||||||
|
|
||||||
local fox = {}
|
|
||||||
do
|
|
||||||
|
|
||||||
local struct_inode = struct {
|
|
||||||
endian = "<",
|
|
||||||
{mode="H"},
|
|
||||||
{uid="H"},
|
|
||||||
{fsize="I6"},
|
|
||||||
{atime="I6"},
|
|
||||||
{ctime="I6"},
|
|
||||||
{mtime="I6"},
|
|
||||||
{dtime="I6"},
|
|
||||||
{gid="H"},
|
|
||||||
{sec_count="I4"},
|
|
||||||
{flags="I4"},
|
|
||||||
{osval="I4"},
|
|
||||||
{dbp0="I4"},
|
|
||||||
{dbp1="I4"},
|
|
||||||
{dbp2="I4"},
|
|
||||||
{dbp3="I4"},
|
|
||||||
{dbp4="I4"},
|
|
||||||
{dbp5="I4"},
|
|
||||||
{dbp6="I4"},
|
|
||||||
{dbp7="I4"},
|
|
||||||
{dbp8="I4"},
|
|
||||||
{dbp9="I4"},
|
|
||||||
{dbp10="I4"},
|
|
||||||
{dbp11="I4"},
|
|
||||||
{sibp="I4"},
|
|
||||||
{dibp="I4"},
|
|
||||||
{tibp="I4"},
|
|
||||||
{gen="H"},
|
|
||||||
{acl="I4"},
|
|
||||||
{fragaddr="I4"},
|
|
||||||
{osval2="c10"}
|
|
||||||
}
|
|
||||||
|
|
||||||
local dirent = struct {
|
|
||||||
endian="<",
|
|
||||||
{inode="I4"},
|
|
||||||
{name_size="H"},
|
|
||||||
{etype="B"}
|
|
||||||
}
|
|
||||||
|
|
||||||
local superblock = struct {
|
|
||||||
endian = "<",
|
|
||||||
{sig="H"},
|
|
||||||
{ver_maj="H"},
|
|
||||||
{ver_min="H"},
|
|
||||||
{state="H"},
|
|
||||||
{total_inodes="I4"},
|
|
||||||
{total_blocks="I4"},
|
|
||||||
{reserved_blocks="I4"},
|
|
||||||
{total_unalloc_blocks="I4"},
|
|
||||||
{total_unalloc_inodes="I4"},
|
|
||||||
{total_unalloc_inodes="I4"},
|
|
||||||
}
|
|
||||||
|
|
||||||
local blkstr = {}
|
|
||||||
|
|
||||||
function fox.proxy(blkdev)
|
|
||||||
-- Read the superblock
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
local tty = {}
|
|
||||||
do
|
|
||||||
local _tty = {}
|
|
||||||
function _tty:getgpu()
|
|
||||||
return self.gpu.address
|
|
||||||
end
|
|
||||||
|
|
||||||
function _tty:getkb()
|
|
||||||
return self.kb.address
|
|
||||||
end
|
|
||||||
|
|
||||||
function _tty:getscreen()
|
|
||||||
return self.screen.address
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
---@section biosfixes "BIOS fixes"
|
|
||||||
|
|
||||||
local _biossupport = {}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
---@page zorya_legacy "Zorya 1.x (Zorya Legacy)"
|
|
||||||
---@doc "Zorya 1.x puts a few things in the global space that need to be removed. These include:"
|
|
||||||
---@doc "- The OEFI library"
|
|
||||||
---@doc "- The Zorya library"
|
|
||||||
---@doc ""
|
|
||||||
---@doc "Note: This *should* also apply to any forks of Zorya Legacy."
|
|
||||||
_biossupport["zoryalegacy"] = {
|
|
||||||
quirks = function()
|
|
||||||
|
|
||||||
zorya = nil
|
|
||||||
end,
|
end,
|
||||||
info = function()
|
postcomp = function(krnl)
|
||||||
|
os.execute("mkdir .docs")
|
||||||
return {
|
local h = io.open("build/kernel/debug.lua")
|
||||||
name = "Zorya",
|
h:write(krnl)
|
||||||
version = {_ZVER//1, tonumber(tostring(_ZVER):match("%.(%d+)")), _ZPAT, string = _ZVER..".".._ZPAT},
|
h:close()
|
||||||
oefiver = oefi.getAPIVersion()
|
print("Generating docs and stripping comments...")
|
||||||
}
|
h = io.popen("lua utils/gendocs.lua .docs 2>.ktmp", "w")
|
||||||
|
h:write(krnl)
|
||||||
|
h:close()
|
||||||
|
h = io.open(".ktmp", "rb")
|
||||||
|
local data = h:read("*a")
|
||||||
|
h:close()
|
||||||
|
os.execute("rm -rf .ktmp")
|
||||||
|
return data
|
||||||
end,
|
end,
|
||||||
detect = function()
|
prearc = function()
|
||||||
|
print("Storing docs...")
|
||||||
return _LOAD == "Zorya"
|
|
||||||
end,
|
end,
|
||||||
name = "zoryalegacy"
|
postarc = function()
|
||||||
}
|
os.execute("rm -rf .docs")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
---@page zorya_neo "Zorya NEO (Zorya 2.0)"
|
|
||||||
---@doc "There's not much to be done for Zorya NEO as the included Zorya module starts Tsuki with a nice enviroment."
|
|
||||||
_biossupport["zoryaneo"] = {
|
|
||||||
quirks = function()
|
|
||||||
|
|
||||||
|
|
||||||
end,
|
end,
|
||||||
info = function()
|
precomp = function()
|
||||||
|
print("Compressing kernel...")
|
||||||
return {
|
|
||||||
name = "Zorya NEO",
|
|
||||||
version = {_ZVER//1, tonumber(tostring(_ZVER):match("%.(%d+)")), _ZPAT, git = _ZGIT, string = _ZVSTR},
|
|
||||||
loader = _ZLOADER
|
|
||||||
}
|
|
||||||
end,
|
end,
|
||||||
detect = function()
|
postcomp = function()
|
||||||
|
print("Writing kernel out...")
|
||||||
|
end
|
||||||
|
}))
|
||||||
|
end
|
||||||
|
|
||||||
return _BIOS == "Zorya NEO"
|
actions[#actions+1] = "kernel"
|
||||||
end,
|
|
||||||
name = "zoryaneo"
|
function actions.crescent()
|
||||||
}
|
os.execute("mkdir -p build/crescent")
|
||||||
|
os.execute("cd extras; lua ../utils/mkvelx.lua crescent/init.lua ../build/crescent/boot.velx")
|
||||||
|
os.execute("cp extras/crescent/bootvelxloader.lua build/crescent/init.lua")
|
||||||
|
end
|
||||||
|
|
||||||
|
actions[#actions+1] = "crescent"
|
||||||
|
|
||||||
|
function actions.velxboot()
|
||||||
|
os.execute("mkdir -p build/velxboot")
|
||||||
|
os.execute("cd extras; luacomp velxboot/init.lua -O ../build/velxboot/bios.lua")
|
||||||
|
os.execute("cd extras; luacomp velxboot/flashvelxboot.lua -O ../build/velxboot/flashvelxboot.lua")
|
||||||
|
end
|
||||||
|
|
||||||
|
actions[#actions+1] = "velxboot"
|
||||||
|
|
||||||
|
function actions.clean()
|
||||||
|
print("Cleaning up...")
|
||||||
|
os.execute("rm -rf .docs")
|
||||||
|
os.execute("rm -rf .ktmp")
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
--[[function actions.debug()
|
||||||
|
actions.kernel(true)
|
||||||
|
actions.crescent()
|
||||||
|
actions.velxboot()
|
||||||
|
actions.clean()
|
||||||
|
end]]
|
||||||
|
|
||||||
|
function actions.all()
|
||||||
|
for i=1, #actions do
|
||||||
|
actions[actions[i]]()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
-- Mount the rootfs
|
if not arg[1] then
|
||||||
vfs.mount()
|
arg[1] = "all"
|
||||||
|
end
|
||||||
|
|
||||||
|
actions[arg[1]]()
|
||||||
|
|
||||||
|
print("Build complete.")
|
11
ksrc/acl.lua
11
ksrc/acl.lua
@ -2,15 +2,20 @@ local acl = {}
|
|||||||
do
|
do
|
||||||
local acl = struct({
|
local acl = struct({
|
||||||
meta = "B",
|
meta = "B",
|
||||||
id = "H",
|
id = "H"
|
||||||
permname = "B"
|
|
||||||
})
|
})
|
||||||
|
|
||||||
local function acl_readstream(stream)
|
local function acl_readstream(stream)
|
||||||
|
local a = acl(stream:read(#acl))
|
||||||
|
local perm = stream:read(a.meta & 0x3f)
|
||||||
|
local
|
||||||
|
end
|
||||||
|
|
||||||
|
function acl.read(stream, dperm, gid, uid)
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function acl.read(stream)
|
function _acl:get_effective_perm(id, group, perm)
|
||||||
|
|
||||||
end
|
end
|
||||||
end
|
end
|
9
ksrc/ads.lua
Normal file
9
ksrc/ads.lua
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
local ads = {}
|
||||||
|
|
||||||
|
function ads.get(path)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function ads.list(path)
|
||||||
|
|
||||||
|
end
|
10
ksrc/archives.lua
Normal file
10
ksrc/archives.lua
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
local archives = {}
|
||||||
|
archives.tsar = (function()
|
||||||
|
--#include "ksrc/arcs/tsar/init.lua"
|
||||||
|
end)()
|
||||||
|
|
||||||
|
function archive.parse(stream, atype)
|
||||||
|
if archives[atype] then
|
||||||
|
return archives[atype].read(stream)
|
||||||
|
end
|
||||||
|
end
|
@ -16,7 +16,7 @@ end
|
|||||||
|
|
||||||
local arc = {}
|
local arc = {}
|
||||||
|
|
||||||
function arc:handle(path)
|
function arc:read(path)
|
||||||
for i=1, #self.tbl do
|
for i=1, #self.tbl do
|
||||||
if (self.tbl[i].name == path and self.tbl[i].mode & 32768 > 0) then
|
if (self.tbl[i].name == path and self.tbl[i].mode & 32768 > 0) then
|
||||||
self.seek(self.tbl[i].pos-self.seek(0))
|
self.seek(self.tbl[i].pos-self.seek(0))
|
||||||
@ -55,12 +55,55 @@ function arc:meta(path)
|
|||||||
return nil, "file not found"
|
return nil, "file not found"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
function arc:stream(path)
|
||||||
|
for i=1, #self.tbl do
|
||||||
|
if (self.tbl[i].name == path) then
|
||||||
|
return kio.create_stream({dev=self.dev, start=self.tbl[i].pos, size=self.tbl[i].filesize, pos=1}, {
|
||||||
|
read = function(self, amt)
|
||||||
|
self.dev:seek("set", self.pos+self.start-1)
|
||||||
|
if (self.pos+amt-1 > self.size) then
|
||||||
|
amt = self.size-self.pos
|
||||||
|
end
|
||||||
|
local dat = self.dev:read(amt)
|
||||||
|
self.pos = self.pos + #dat
|
||||||
|
return dat
|
||||||
|
end,
|
||||||
|
seek = function(self, whence, amt)
|
||||||
|
self.pos = kio.calc_seek(whence, amt, self.size, self.pos)
|
||||||
|
return self.pos
|
||||||
|
end,
|
||||||
|
write = function(self)
|
||||||
|
return kio.get_error(kio.errno.UNSUPPORTED_OPERATION)
|
||||||
|
end,
|
||||||
|
close = function(self)
|
||||||
|
|
||||||
|
end
|
||||||
|
})
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
function arc:trailer()
|
||||||
|
self.dev:seek("set", self.tbl.trailer.pos)
|
||||||
|
return self.dev:read(self.tbl.trailer.filesize)
|
||||||
|
end
|
||||||
|
|
||||||
function arc:close()
|
function arc:close()
|
||||||
self.close()
|
self.close()
|
||||||
end
|
end
|
||||||
|
|
||||||
return {
|
return {
|
||||||
read = function(read, seek, close)
|
read = function(dev)
|
||||||
|
local function read(a)
|
||||||
|
return dev:read(a)
|
||||||
|
end
|
||||||
|
local function seek(a)
|
||||||
|
return dev:seek("cur", a)
|
||||||
|
end
|
||||||
|
local function close()
|
||||||
|
return dev:close()
|
||||||
|
end
|
||||||
|
local start = seek(0)
|
||||||
local tbl = {}
|
local tbl = {}
|
||||||
local lname = ""
|
local lname = ""
|
||||||
while lname ~= "TRAILER!!!" do
|
while lname ~= "TRAILER!!!" do
|
||||||
@ -72,8 +115,10 @@ return {
|
|||||||
lname = et.name
|
lname = et.name
|
||||||
if lname ~= "TRAILER!!!" then
|
if lname ~= "TRAILER!!!" then
|
||||||
tbl[#tbl+1] = et
|
tbl[#tbl+1] = et
|
||||||
|
else
|
||||||
|
tbl.trailer = et
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
return setmetatable({tbl = tbl, read = read, seek = seek, close = close}, {__index=arc})
|
return setmetatable({tbl = tbl, read = read, seek = seek, close = close, dev=dev, start=true}, {__index=arc})
|
||||||
end
|
end
|
||||||
}
|
}
|
1
ksrc/bios/unknown/detect.lua
Normal file
1
ksrc/bios/unknown/detect.lua
Normal file
@ -0,0 +1 @@
|
|||||||
|
return true
|
2
ksrc/bios/unknown/docs.lua
Normal file
2
ksrc/bios/unknown/docs.lua
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
---@page unknown "Unknown"
|
||||||
|
---@doc "This is for if Tsuki doesn't know what BIOS is in use."
|
4
ksrc/bios/unknown/info.lua
Normal file
4
ksrc/bios/unknown/info.lua
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
return {
|
||||||
|
name = "Unknown",
|
||||||
|
version = {0, 0, 0, string="0.0.0"}
|
||||||
|
}
|
0
ksrc/bios/unknown/quirks.lua
Normal file
0
ksrc/bios/unknown/quirks.lua
Normal file
@ -1,5 +1,7 @@
|
|||||||
---@section biosfixes "BIOS fixes"
|
---@section biosfixes "BIOS fixes"
|
||||||
|
|
||||||
|
@[[do
|
||||||
|
local i=1]]
|
||||||
local _biossupport = {}
|
local _biossupport = {}
|
||||||
@[[function biosfix(bios)]]
|
@[[function biosfix(bios)]]
|
||||||
--#include @[{"ksrc/bios/"..bios.."/docs.lua"}]
|
--#include @[{"ksrc/bios/"..bios.."/docs.lua"}]
|
||||||
@ -13,11 +15,16 @@ _biossupport["@[{bios}]"] = {
|
|||||||
detect = function()
|
detect = function()
|
||||||
--#include @[{"ksrc/bios/"..bios.."/detect.lua"}]
|
--#include @[{"ksrc/bios/"..bios.."/detect.lua"}]
|
||||||
end,
|
end,
|
||||||
name = "@[{bios}]"
|
name = "@[{bios}]",
|
||||||
|
id = @[{i}]
|
||||||
}
|
}
|
||||||
|
_biossupport[@[{i}]] = "@[{bios}]"
|
||||||
|
@[[i=i+1]]
|
||||||
@[[end]]
|
@[[end]]
|
||||||
|
|
||||||
@[[biosfix("zoryalegacy")]]
|
@[[biosfix("zoryalegacy")]]
|
||||||
@[[biosfix("zoryaneo")]]
|
@[[biosfix("zoryaneo")]]
|
||||||
|
|
||||||
|
@[[biosfix("unknown")]]
|
||||||
@[[biosfix = nil]]
|
@[[biosfix = nil]]
|
||||||
|
@[[end]]
|
@ -0,0 +1,5 @@
|
|||||||
|
local eeprom = {}
|
||||||
|
|
||||||
|
function eeprom.proxy(addr)
|
||||||
|
|
||||||
|
end
|
@ -0,0 +1,4 @@
|
|||||||
|
--#include "ksrc/blk/eeprom.lua"
|
||||||
|
--#include "ksrc/blk/hdd.lua"
|
||||||
|
--#include "ksrc/blk/partition.lua"
|
||||||
|
--#include "ksrc/blk/promcard.lua"
|
@ -7,7 +7,28 @@ local zlua = (function()
|
|||||||
--#include "ksrc/execs/zlua/init.lua"
|
--#include "ksrc/execs/zlua/init.lua"
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
local lua = (function()
|
||||||
|
--#include "ksrc/execs/lua/init.lua"
|
||||||
|
end)
|
||||||
|
|
||||||
-- Executable loading process:
|
-- Executable loading process:
|
||||||
-- - Link
|
-- - Link
|
||||||
-- - Load
|
-- - Load
|
||||||
-- - Execute
|
-- - Execute
|
||||||
|
|
||||||
|
function exec.loadfile(path, env, runinfo)
|
||||||
|
local stat = vfs.stat(path)
|
||||||
|
if (stat & 0x400 > 0) then
|
||||||
|
runinfo.gid = stat.gid
|
||||||
|
end
|
||||||
|
if (stat & 0x800 > 0) then
|
||||||
|
runinfo.uid = stat.uid
|
||||||
|
end
|
||||||
|
if (velx.identify(path)) then
|
||||||
|
|
||||||
|
elseif (zlua.identify(path)) then
|
||||||
|
|
||||||
|
else -- Load Lua...if we can.
|
||||||
|
|
||||||
|
end
|
||||||
|
end
|
0
ksrc/execs/lua/init.lua
Normal file
0
ksrc/execs/lua/init.lua
Normal file
@ -24,7 +24,11 @@ function velx.identify(path)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function velx.load(path)
|
function velx.load(path)
|
||||||
|
local h = io.open(path, "rb")
|
||||||
|
local header = velx_spec(h:read(#velx_spec))
|
||||||
|
local code = h:read(header.psize)
|
||||||
|
h:seek("cur", lsize)
|
||||||
|
local sig = h:read(header.ssize)
|
||||||
end
|
end
|
||||||
|
|
||||||
function velx.verify(path)
|
function velx.verify(path)
|
||||||
|
1
ksrc/fs/arcfs/init.lua
Normal file
1
ksrc/fs/arcfs/init.lua
Normal file
@ -0,0 +1 @@
|
|||||||
|
local afs = {}
|
21
ksrc/fs/foxfs/ads.lua
Normal file
21
ksrc/fs/foxfs/ads.lua
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
function prox:getadses(path)
|
||||||
|
local inode = fox_getnode(self, path)
|
||||||
|
local adsl = fox_readdir(self, inode.ads)
|
||||||
|
return adsl
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:makeads(path, stream)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:getads(path, stream)
|
||||||
|
local inode = fox_getnode(self, path)
|
||||||
|
local adsl = fox_readdir(self, inode.ads)
|
||||||
|
for i=1, do
|
||||||
|
if (adsl[i].name == stream) then
|
||||||
|
local node = fox_getinode(self, adsl[i].inode)
|
||||||
|
return {node=node, pos=1, mode=mode, dev=self}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
return nil, "not found"
|
||||||
|
end
|
@ -4,3 +4,11 @@ local dirent = struct {
|
|||||||
{name_size="H"},
|
{name_size="H"},
|
||||||
{etype="B"}
|
{etype="B"}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
local function fox_readdir(self, inode)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:list(path)
|
||||||
|
|
||||||
|
end
|
21
ksrc/fs/foxfs/filehand.lua
Normal file
21
ksrc/fs/foxfs/filehand.lua
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
function prox:open(path, mode)
|
||||||
|
local node = fox_getnode(self, path)
|
||||||
|
if not node then return nil, "file not found" end
|
||||||
|
return {node=node, pos=1, mode=mode, dev=self}
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:read(hand, amt)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:write(hand, data)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:seek(hand, amt)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function prox:close(hand)
|
||||||
|
|
||||||
|
end
|
@ -7,11 +7,16 @@ do
|
|||||||
|
|
||||||
local prox = {}
|
local prox = {}
|
||||||
|
|
||||||
function fox.proxy(blkdev)
|
function fox.proxy(dev)
|
||||||
-- Read the superblock
|
-- Read the superblock
|
||||||
|
sb:seek("set", 1025)
|
||||||
|
local sb = superblock(dev:read(#superblock))
|
||||||
|
local prox = {
|
||||||
|
super = sb
|
||||||
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
local function fox_getinode(prox, inode)
|
local function fox_getinode(prox, inode)
|
||||||
prox.dev:size()
|
|
||||||
end
|
end
|
||||||
end
|
end
|
@ -27,7 +27,7 @@ local struct_inode = struct {
|
|||||||
{dibp="I4"},
|
{dibp="I4"},
|
||||||
{tibp="I4"},
|
{tibp="I4"},
|
||||||
{gen="H"},
|
{gen="H"},
|
||||||
{acl="I4"},
|
{ads="I4"},
|
||||||
{fragaddr="I4"},
|
{fragaddr="I4"},
|
||||||
{osval2="c10"}
|
{osval2="c10"}
|
||||||
}
|
}
|
@ -1,5 +1,12 @@
|
|||||||
|
--#include "ksrc/kstrings.lua"
|
||||||
|
--#include "ksrc/kargs.lua"
|
||||||
|
--#include "ksrc/kio.lua"
|
||||||
|
--#include "ksrc/vfs.lua"
|
||||||
--#include "ksrc/struct.lua"
|
--#include "ksrc/struct.lua"
|
||||||
--#include "ksrc/string.lua"
|
--#include "ksrc/string.lua"
|
||||||
|
--#include "ksrc/archives.lua"
|
||||||
|
--#include "ksrc/ads.lua"
|
||||||
|
--#include "ksrc/blkdev.lua"
|
||||||
--#include "ksrc/acl.lua"
|
--#include "ksrc/acl.lua"
|
||||||
--#include "ksrc/security.lua"
|
--#include "ksrc/security.lua"
|
||||||
--#include "ksrc/exec.lua"
|
--#include "ksrc/exec.lua"
|
||||||
@ -7,7 +14,25 @@
|
|||||||
--#include "ksrc/tty.lua"
|
--#include "ksrc/tty.lua"
|
||||||
--#include "ksrc/biosfixes.lua"
|
--#include "ksrc/biosfixes.lua"
|
||||||
--#include "ksrc/buffer.lua"
|
--#include "ksrc/buffer.lua"
|
||||||
--#include "ksrc/kio.lua"
|
--#include "ksrc/threads.lua"
|
||||||
|
--#include "ksrc/net.lua"
|
||||||
|
|
||||||
-- Mount the rootfs
|
kio.dmesg(1, "Starting Tsuki kernel.")
|
||||||
vfs.mount()
|
kio.init()
|
||||||
|
|
||||||
|
-- Mount the initramfs, if there is one.
|
||||||
|
if (kargs.iramfs or kargs.root == "$") then
|
||||||
|
vfs.mount("/", arcfs.proxy(_ARCHIVE))
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Eventually...
|
||||||
|
do
|
||||||
|
local pty = tty.get(0)
|
||||||
|
kio.dmesg(1, "Passing off to init.")
|
||||||
|
exec.startfile(kargs.init or "/bin/init.velx", true, {
|
||||||
|
uid = 0,
|
||||||
|
gid = 0,
|
||||||
|
tty = pty,
|
||||||
|
args = {kargs}
|
||||||
|
})
|
||||||
|
end
|
0
ksrc/kargs.lua
Normal file
0
ksrc/kargs.lua
Normal file
295
ksrc/kio.lua
295
ksrc/kio.lua
@ -1,8 +1,299 @@
|
|||||||
---@module kio "Kernel I/O"
|
@[[if not svar.get("PRINT_DMESG_LEVEL") then
|
||||||
local kio = {}
|
svar.set("PRINT_DMESG_LEVEL", "1")
|
||||||
|
end]]
|
||||||
|
|
||||||
|
---@module kio "Kernel I/O"
|
||||||
|
kio = {}
|
||||||
|
|
||||||
|
local _stream = {}
|
||||||
|
function _stream:read(amt)
|
||||||
|
local buf = ""
|
||||||
|
local lc = ""
|
||||||
|
if (amt == "*l") then -- Our line ending is \n
|
||||||
|
repeat
|
||||||
|
lc = self.proto.read(self.udat, 1)
|
||||||
|
if (lc ~= "\n") then
|
||||||
|
buf = buf .. (lc or "")
|
||||||
|
end
|
||||||
|
until not lc or lc == "" or lc == "\n"
|
||||||
|
return buf
|
||||||
|
--elseif (amt == "*n") then
|
||||||
|
|
||||||
|
elseif (amt == "*a") then
|
||||||
|
local pos = self:seek("cur", 0)
|
||||||
|
local send = self:seek("end", 0)
|
||||||
|
self:seek("set", pos)
|
||||||
|
amt = send - pos
|
||||||
|
end
|
||||||
|
return self.proto.read(self.udat, amt)
|
||||||
|
end
|
||||||
|
|
||||||
|
function _stream:write(data)
|
||||||
|
return self.proto.write(self.udat, data)
|
||||||
|
end
|
||||||
|
|
||||||
|
function _stream:seek(whence, amt)
|
||||||
|
if not amt then
|
||||||
|
amt = whence or 0
|
||||||
|
whence = "cur"
|
||||||
|
end
|
||||||
|
return self.proto.seek(self.udat, whence, amt)
|
||||||
|
end
|
||||||
|
|
||||||
|
function _stream:eof()
|
||||||
|
local pos = self:seek("cur", 0)
|
||||||
|
local send = self:seek("end", 0)
|
||||||
|
self:seek("set", pos)
|
||||||
|
return pos == send
|
||||||
|
end
|
||||||
|
|
||||||
|
function _stream:close()
|
||||||
|
return self.proto.close(self.udat)
|
||||||
|
end
|
||||||
|
|
||||||
|
function _stream:size()
|
||||||
|
local pos = self:seek("cur", 0)
|
||||||
|
local send = self:seek("end", 0)
|
||||||
|
self:seek("set", pos)
|
||||||
|
return send
|
||||||
|
end
|
||||||
|
|
||||||
|
function kio.create_stream(udat, proto)
|
||||||
|
return setmetatable({udat=udat, proto=proto}, {__index=_stream})
|
||||||
|
end
|
||||||
|
|
||||||
|
@[[local kio_errc = 0
|
||||||
|
function kio_err(name, rtn)]]
|
||||||
|
kio.errno["@[{name}]"] = @[{kio_errc}]
|
||||||
|
kio_errors[@[{kio_errc}]] = "@[{rtn}]"
|
||||||
|
@[[kio_errc = kio_errc + 1
|
||||||
|
end]]
|
||||||
|
|
||||||
|
kio.errno = {}
|
||||||
|
local kio_errors = {}
|
||||||
|
@[[
|
||||||
|
kio_err("FILE_NOT_FOUND", "not found")
|
||||||
|
kio_err("FILE_DIRECTORY", "file is a directory")
|
||||||
|
kio_err("DEV_TIMEOUT", "device timeout")
|
||||||
|
kio_err("IO_ERROR", "generic i/o error")
|
||||||
|
kio_err("UNSUPPORTED_OPERATION", "unsupported operation")
|
||||||
|
kio_err("NOT_ALLOWED", "not allowed")
|
||||||
|
kio_err("TOO_MANY_SYMLINKS", "too many symlinks")
|
||||||
|
kio_err("DEV_FULL", "device is full")
|
||||||
|
kio_err("DEV_READ_ONLY", "device is read only")
|
||||||
|
]]
|
||||||
|
|
||||||
|
kio.geterror = function(e)
|
||||||
|
return nil, kio_errors[e] or "generic error"
|
||||||
|
end
|
||||||
|
|
||||||
|
function kio.invoke(path, method, ...)
|
||||||
|
local dev, rpath = vfs.resolve(path)
|
||||||
|
return dev.dev[method](dev.dev, rpath, ...)
|
||||||
|
end
|
||||||
|
|
||||||
|
function kio.has_ads(path)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function kio.ads_exists(path, ads)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function kio.has_acl(path)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func calc_seek
|
||||||
|
---@arg whence string "Like io.seek's whence."
|
||||||
|
---@arg amt integer "The amount to seek."
|
||||||
|
---@arg size integer "The size of the stream."
|
||||||
|
---@arg pos integer "The current position."
|
||||||
|
---@return integer "The new position"
|
||||||
|
---@desc "This function calculates the new position for seeking."
|
||||||
|
function kio.calc_seek(whence, amt, size, pos)
|
||||||
|
if (whence == "cur") then
|
||||||
|
pos = pos + amt
|
||||||
|
elseif (whence == "end") then
|
||||||
|
pos = size + amt
|
||||||
|
elseif (whence == "set") then
|
||||||
|
pos = amt
|
||||||
|
end
|
||||||
|
if pos > size then
|
||||||
|
pos = size
|
||||||
|
elseif pos < 1 then
|
||||||
|
pos = 1
|
||||||
|
end
|
||||||
|
return pos
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func filestream
|
||||||
|
---@arg path string "Path to the file"
|
||||||
|
---@arg mode string "File mode"
|
||||||
|
---@return stream "The stream for the file."
|
||||||
|
---@desc "This creates a stream from a file."
|
||||||
|
function kio.filestream(path, mode)
|
||||||
|
local dev, rpath = vfs.resolve(path)
|
||||||
|
local h = dev:open(rpath, mode)
|
||||||
|
local stat = dev:stat(rpath)
|
||||||
|
return kio.create_stream({dev=dev, hand=h, stat=stat}, {
|
||||||
|
read = function(self, amt)
|
||||||
|
return self.dev:read(self.hand, amt)
|
||||||
|
end,
|
||||||
|
seek = function(self, whence, amt)
|
||||||
|
local pos = self.dev:seek(self.hand, 0)
|
||||||
|
local npos = kio.calc_seek(whence, amt, self.stat.size, pos)
|
||||||
|
return self.dev:seek(self.hand, npos-pos)
|
||||||
|
end,
|
||||||
|
write = function(self, data)
|
||||||
|
return self.dev:write(self.hand, data)
|
||||||
|
end,
|
||||||
|
close = function(self)
|
||||||
|
return self.dev:close(self.hand)
|
||||||
|
end
|
||||||
|
})
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func dir
|
||||||
|
---@arg udat table "The data to pass to to prototype"
|
||||||
|
---@arg proto function "The prototype function for the iterator"
|
||||||
|
---@return function "The iterator."
|
||||||
|
---@desc "Creates a directory iterator."
|
||||||
|
function kio.dir(udat, proto)
|
||||||
|
return function()
|
||||||
|
return proto(udat)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func memstream
|
||||||
|
---@arg str string "The string to create a stream of."
|
||||||
|
---@arg write boolean "If the stream should be writable or not."
|
||||||
|
---@return stream "The memory stream."
|
||||||
|
---@desc "Creates a memory stream."
|
||||||
|
---@note "stream:close() returns the string."
|
||||||
|
function kio.memstream(str, write)
|
||||||
|
return kio.create_stream({str=str, pos=1, write=write}, {
|
||||||
|
read = function(self, amt)
|
||||||
|
local dat = self.str:sub(self.pos, self.pos+amt-1)
|
||||||
|
self.pos = self.pos+#dat
|
||||||
|
return dat
|
||||||
|
end,
|
||||||
|
write = function(self, dat)
|
||||||
|
if (write) then
|
||||||
|
local startstr = self.str:sub(1, self.pos-1)
|
||||||
|
local endstr = self.str:sub(self.pos+#dat)
|
||||||
|
self.str = startstr..dat..endstr
|
||||||
|
self.pos = self.pos + #dat
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
seek = function(self, whence, amt)
|
||||||
|
self.pos = kio.calc_seek(whence, amt, #self.str, self.pos)
|
||||||
|
return self.pos
|
||||||
|
end,
|
||||||
|
close = function(self)
|
||||||
|
return self.str
|
||||||
|
end
|
||||||
|
})
|
||||||
|
end
|
||||||
|
|
||||||
|
kio.loglevel = {
|
||||||
|
DEBUG = 0,
|
||||||
|
INFO = 1,
|
||||||
|
WARNING = 2,
|
||||||
|
ERROR = 3,
|
||||||
|
PANIC = 255
|
||||||
|
}
|
||||||
|
|
||||||
|
kio.levels = {
|
||||||
|
[0] = "DEBUG",
|
||||||
|
"INFO",
|
||||||
|
"WARNING",
|
||||||
|
"ERROR",
|
||||||
|
[255] = "PANIC"
|
||||||
|
}
|
||||||
|
|
||||||
|
---@func dprint
|
||||||
|
---@arg level integer "The log level"
|
||||||
|
---@arg status string "The message."
|
||||||
|
---@desc "This method logs to the kernel log and wherever else is set up to be printed to."
|
||||||
|
function kio.dprint(level, status)
|
||||||
|
local stack = {}
|
||||||
|
local lkexec = {}
|
||||||
|
local i = 0
|
||||||
|
while lkexec do
|
||||||
|
lkexec = debug.getinfo(i)
|
||||||
|
stack[#stack+1] = lkexec
|
||||||
|
end
|
||||||
|
local src = stack[#stack].source:sub(2)
|
||||||
|
local spart = vfs.parts(src)
|
||||||
|
local exec = spart[#spart]:match("^(.+)%.([^%.]+)$")
|
||||||
|
local message = string.format("[%.2f] [%s] [%s] %s", computer.uptime(), levels[level], exec, status)
|
||||||
|
dmesgs[#dmesgs+1] = {ut=computer.uptime,lvl=level,x=exec,st=status}
|
||||||
|
if (level < $[{PRINT_DMESG_LEVEL}]) then
|
||||||
|
sig.push {
|
||||||
|
type = "dprint",
|
||||||
|
msg = message
|
||||||
|
}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func dmesg
|
||||||
|
---@see kio.dprint
|
||||||
|
kio.dmesg = dprint
|
||||||
|
|
||||||
|
---@func panic
|
||||||
|
---@arg msg string "The error message to display."
|
||||||
|
function kio.panic(msg)
|
||||||
|
dmesg(255, "Kernel panic!")
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func create_pipe
|
||||||
|
---@return stream "Pipe in"
|
||||||
|
---@return stream "Pipe out"
|
||||||
|
---@desc "Creates a pipe."
|
||||||
|
function kio.create_pipe()
|
||||||
|
local pipecore = kio.memstream()
|
||||||
|
local pipein = kio.create_stream({
|
||||||
|
dat = pipecore
|
||||||
|
}, {
|
||||||
|
read = function()
|
||||||
|
-- no
|
||||||
|
end,
|
||||||
|
seek = function()
|
||||||
|
-- no
|
||||||
|
end,
|
||||||
|
write = function(self, dat)
|
||||||
|
self.dat:seek("end", 0)
|
||||||
|
self.dat:write(dat)
|
||||||
|
end,
|
||||||
|
close = function()
|
||||||
|
-- *no*
|
||||||
|
end
|
||||||
|
})
|
||||||
|
local pipeout = kio.create_stream({
|
||||||
|
dat = pipecore,
|
||||||
|
pos = 1
|
||||||
|
}, {
|
||||||
|
read = function(self, amt)
|
||||||
|
self.dat:seek("set", self.pos)
|
||||||
|
local dat = self.dat:read()
|
||||||
|
self.pos = self.pos+#dat
|
||||||
|
return dat
|
||||||
|
end,
|
||||||
|
seek = function()end,
|
||||||
|
write = function()end,
|
||||||
|
close = function()end
|
||||||
|
})
|
||||||
|
return pipein, pipeout
|
||||||
|
end
|
||||||
|
|
||||||
|
---@func init
|
||||||
|
---@desc "Only called once. Sets up the kio library."
|
||||||
|
function kio.init()
|
||||||
---@func create_buffer
|
---@func create_buffer
|
||||||
---@arg blocking boolean "True if read calls to a buffer that doesn't contain enough data block."
|
---@arg blocking boolean "True if read calls to a buffer that doesn't contain enough data block."
|
||||||
---@arg pid integer "This is set to the PID of the process which handles the buffers."
|
---@arg pid integer "This is set to the PID of the process which handles the buffers."
|
||||||
---@return table "The buffer for use anywhere."
|
---@return table "The buffer for use anywhere."
|
||||||
kio.create_buffer = create_buffer
|
kio.create_buffer = create_buffer
|
||||||
|
kio.init = false
|
||||||
|
end
|
6
ksrc/kstrings.lua
Normal file
6
ksrc/kstrings.lua
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
_KINFO = {
|
||||||
|
name = "Tsuki",
|
||||||
|
release = "$[{TSUKI_RELEASE}]",
|
||||||
|
version = "$[{TSUKI_VERSION}]",
|
||||||
|
machine = "$[{TSUKI_TARGET}]", -- OC or LuPI2
|
||||||
|
}
|
6
ksrc/net.lua
Normal file
6
ksrc/net.lua
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
--#include "ksrc/net/tsukinet/init.lua"
|
||||||
|
|
||||||
|
local net = {}
|
||||||
|
function net.open(netinfo)
|
||||||
|
|
||||||
|
end
|
6
ksrc/stdlib/err.lua
Normal file
6
ksrc/stdlib/err.lua
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
_P.pcall = pcall
|
||||||
|
_P.xpcall = xpcall
|
||||||
|
|
||||||
|
_P.error = {}
|
||||||
|
_P.error.geterror = kio.geterror
|
||||||
|
_P.error.errno = kio.errno
|
@ -4,5 +4,7 @@ function _P.load(...)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
--#include "ksrc/stdlib/err.lua"
|
||||||
--#include "ksrc/stdlib/string.lua"
|
--#include "ksrc/stdlib/string.lua"
|
||||||
--#include "ksrc/stdlib/thread.lua"
|
--#include "ksrc/stdlib/thread.lua"
|
||||||
|
--#include "ksrc/stdlib/err.lua"
|
0
ksrc/stdlib/io.lua
Normal file
0
ksrc/stdlib/io.lua
Normal file
@ -1,3 +1,5 @@
|
|||||||
|
string.newline = "\n"
|
||||||
|
|
||||||
function string.trim(self)
|
function string.trim(self)
|
||||||
return self:gsub("^%s+", ""):gsub("%s+$", "")
|
return self:gsub("^%s+", ""):gsub("%s+$", "")
|
||||||
end
|
end
|
||||||
|
13
ksrc/vfs.lua
Normal file
13
ksrc/vfs.lua
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
local vfs = {}
|
||||||
|
|
||||||
|
function vfs.mount(path, proxy)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function vfs.resolve(path)
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
function vfs.umount(pathorproxy)
|
||||||
|
|
||||||
|
end
|
BIN
tkrnl.velx
BIN
tkrnl.velx
Binary file not shown.
@ -157,7 +157,7 @@ for line in io.stdin:lines() do
|
|||||||
}
|
}
|
||||||
elseif (rline:match("^%-@return") and cfunc.type == "func") then
|
elseif (rline:match("^%-@return") and cfunc.type == "func") then
|
||||||
local args = parse_line(rline:sub(10))
|
local args = parse_line(rline:sub(10))
|
||||||
cfunc.ret[#cfunc.args+1] = {
|
cfunc.ret[#cfunc.ret+1] = {
|
||||||
type = args[1],
|
type = args[1],
|
||||||
doc = args[2],
|
doc = args[2],
|
||||||
}
|
}
|
||||||
@ -169,7 +169,17 @@ for line in io.stdin:lines() do
|
|||||||
elseif (rline:match("^%-@see")) then
|
elseif (rline:match("^%-@see")) then
|
||||||
local args = parse_line(rline:sub(7))
|
local args = parse_line(rline:sub(7))
|
||||||
cfunc.doc[#cfunc.doc+1] = {
|
cfunc.doc[#cfunc.doc+1] = {
|
||||||
doc = "See \27_S"..arg[2].."\27_E"
|
doc = "See \27_S"..args[1].."\27_E"
|
||||||
|
}
|
||||||
|
elseif (rline:match("^%-@note")) then
|
||||||
|
local args = parse_line(rline:sub(8))
|
||||||
|
cfunc.doc[#cfunc.doc+1] = {
|
||||||
|
doc = "NOTE: "..args[1]
|
||||||
|
}
|
||||||
|
elseif (rline:match("^%-@desc")) then
|
||||||
|
local args = parse_line(rline:sub(8))
|
||||||
|
cfunc.doc[#cfunc.doc+1] = {
|
||||||
|
doc = args[1]
|
||||||
}
|
}
|
||||||
elseif (rline:match("^%-@vararg")) then
|
elseif (rline:match("^%-@vararg")) then
|
||||||
cfunc.vararg = true
|
cfunc.vararg = true
|
||||||
@ -237,7 +247,7 @@ for i=1, #docs do
|
|||||||
else
|
else
|
||||||
rettext = "No return."
|
rettext = "No return."
|
||||||
end
|
end
|
||||||
docc = docc .. fun .. "\n\nArguments:\n"..argtext.."\n\nReturns:\n"..rettext
|
docc = docc .. fun .. "\n\nArguments:\n"..argtext.."\n\nReturns:\n"..rettext.."\n\n"
|
||||||
else
|
else
|
||||||
docc = docc .. docs[i].methods[j].print_name .. "\n\n"
|
docc = docc .. docs[i].methods[j].print_name .. "\n\n"
|
||||||
end
|
end
|
||||||
|
Loading…
Reference in New Issue
Block a user