216 lines
5.9 KiB
Plaintext
216 lines
5.9 KiB
Plaintext
local function rand()
|
|
if math.random(0,1)==0 then return true else return false end
|
|
end
|
|
function coroutine.resumeWithTimeout(CORO, TIME, ...)
|
|
return rand(), coroutine.resume(CORO, ...)
|
|
end
|
|
|
|
-- Copyright (C) 2025 ASTRONAND
|
|
-- Get boot arguments
|
|
_G.component=component
|
|
local bootArgs=({...})[1]
|
|
local bootDrive=bootArgs.bootDrive
|
|
local LOG_TEXT=""
|
|
local log={}
|
|
local term
|
|
local bootData=load("return "..(bootDrive:open("var/log/kernel/bootData").read() or "{}"))()
|
|
local computer=component.getFirst("computer")
|
|
local startup=true
|
|
local osleep=sleep
|
|
local oldYield=coroutine.yield
|
|
|
|
function coroutine.yield(...)
|
|
if not startup then
|
|
if coroutine.isyieldable(coroutine.running()) then
|
|
oldYield(...)
|
|
end
|
|
end
|
|
end
|
|
|
|
-- Find terminal(s)
|
|
local terminals={}
|
|
for i,v in component.list() do
|
|
if i == "screen" then
|
|
terminals[#terminals+1] = v
|
|
end
|
|
end
|
|
term={
|
|
print=function(...)
|
|
for _,v in ipairs(terminals) do
|
|
v.print(...)
|
|
end
|
|
end,
|
|
printInline=function(...)
|
|
for _,v in ipairs(terminals) do
|
|
v.printInline(...)
|
|
end
|
|
end,
|
|
clear=function(...)
|
|
for _,v in ipairs(terminals) do
|
|
v.clear(...)
|
|
end
|
|
end
|
|
}
|
|
|
|
term.print("Welcome to Hyperion OS")
|
|
-- Difine logging lib
|
|
local function getPName(func)
|
|
if type(func) == "function" then
|
|
getPName=func
|
|
end
|
|
return "Hyprkrnl"
|
|
end
|
|
|
|
function log.log(text)
|
|
if startup then term.print("[ OK ] "..getPName()..": "..text) end
|
|
LOG_TEXT=LOG_TEXT.."[ OK ] "..getPName()..": "..text.."\n"
|
|
end
|
|
|
|
function log.error(text)
|
|
if startup then term.print("[FAILED] "..getPName()..": "..text) end
|
|
LOG_TEXT=LOG_TEXT.."[FAILED] "..getPName()..": "..text.."\n"
|
|
end
|
|
|
|
function log.warn(text)
|
|
if startup then term.print("[ WARN ] "..getPName()..": "..text) end
|
|
LOG_TEXT=LOG_TEXT.."[ WARN ] "..getPName()..": "..text.."\n"
|
|
end
|
|
|
|
function log.raw(text)
|
|
if startup then term.print(" "..getPName()..": "..text) end
|
|
LOG_TEXT=LOG_TEXT.." "..getPName()..": "..text.."\n"
|
|
end
|
|
|
|
function log.get()
|
|
return LOG_TEXT
|
|
end
|
|
|
|
local function t2t(table)
|
|
local output = "{"
|
|
for i,v in pairs(table) do
|
|
local coma=true
|
|
if type(i) == "string" then
|
|
output=output.."[\""..i.."\"]="
|
|
end
|
|
if type(v) == "table" then
|
|
if v == table then
|
|
output=string.sub(output,1,#output-(#i+1))
|
|
coma=false
|
|
else
|
|
output=output..t2t(v)
|
|
end
|
|
elseif type(v) == "string" then
|
|
output=output.."[=["..v.."]=]"
|
|
elseif type(v) == "number" then
|
|
output=output..tostring(v)
|
|
elseif type(v) == "function" then
|
|
output=string.sub(output,1,#output-(#i+1))
|
|
coma=false
|
|
end
|
|
if coma then
|
|
output=output..","
|
|
end
|
|
end
|
|
if #table>0 or string.sub(output,#output,#output) == "," then
|
|
output=string.sub(output,1,#output-1)
|
|
end
|
|
output=output.."}"
|
|
return output
|
|
end
|
|
|
|
-- My favorite function
|
|
local function PANIC(err,lvl)
|
|
term.clear()
|
|
term.print(LOG_TEXT)
|
|
term.printInline("KERNEL PANIC: "..err)
|
|
computer.beep(800,0.2)
|
|
osleep(0.02)
|
|
if err==bootData.prevError then
|
|
bootData.errorCount=bootData.errorCount+1
|
|
else
|
|
bootData.prevError=err
|
|
bootData.errorCount=0
|
|
end
|
|
bootDrive:open("var/log/kernel/bootData").write(t2t(bootData))
|
|
if bootData.errorCount < 4 then
|
|
term.print("")
|
|
term.print("Atempting reboot...")
|
|
osleep(0.5)
|
|
computer.reboot()
|
|
elseif bootData.errorCount > 3 then
|
|
term.print("")
|
|
term.print("boot determined to be unrecoverable...")
|
|
osleep(0.5)
|
|
computer.shutdown()
|
|
end
|
|
while true do
|
|
|
|
end
|
|
end
|
|
|
|
local function runAsKernel(path, args)
|
|
local ok,err,extra = pcall(load(bootDrive:open(path):read()), args)
|
|
if not ok then
|
|
PANIC(path.." failed to load/execute err:\n"..(err or ""))
|
|
end
|
|
return err,extra
|
|
end
|
|
|
|
-- Add libray modifications+
|
|
for _,v in ipairs(bootDrive:list("/sys/kernel/glib")) do
|
|
log.raw("running "..v)
|
|
runAsKernel("/sys/kernel/glib/"..v)
|
|
log.log("Loaded "..v)
|
|
end
|
|
log.log("Finished loading global librarys")
|
|
local sudoMaster={}
|
|
local auth=runAsKernel("sys/kernel/userManager.sys",{masterKey=sudoMaster,bootDrive=bootDrive})
|
|
log.log("Created UE Manager")
|
|
local fs=runAsKernel("sys/kernel/filesystem.sys",{bootDrive=bootDrive,auth=auth})
|
|
log.log("Initailized filesystem")
|
|
local io=runAsKernel("sys/kernel/ioManager.sys",{masterKey=sudoMaster})
|
|
log.log("Started ioManager")
|
|
local packages={filesystem=fs, auth=auth, logging=log, term=term}
|
|
local req=runAsKernel("sys/modules/require",{filesystem=fs,logging=log, preload=packages})
|
|
log.log("Loaded require")
|
|
local setRequire
|
|
local requ=req.makeRequire("lib/?;lib/?/init;sys/modules/?;sys/modules/?/init",packages)
|
|
_G.require, setRequire = requ.require, requ.load
|
|
setRequire("require",req)
|
|
log.log("Initailized require")
|
|
|
|
local code=fs.open("sys/kernel/hypervisor.sys","xe", _G)
|
|
|
|
if not code then
|
|
PANIC("System failed to load")
|
|
end
|
|
local ok, system=pcall(code, {masterKey=sudoMaster, setRequire=setRequire, pname=getPName})
|
|
if not ok then
|
|
PANIC("Hypervisor failed to execute ERR:\n"..hypervisor)
|
|
end
|
|
log.log("Loaded hypervisor")
|
|
log.raw("Making kernel process")
|
|
|
|
hypervisor(function()
|
|
local hpv=require("hypervisor")
|
|
local thread=require("thread")
|
|
log.log("Created kernel process")
|
|
hpv.createProcessFromFile("sys/os/init.lua", "systemd")
|
|
thread.create(function()
|
|
while true do
|
|
local event = {computer.getMachineEvent()}
|
|
if event[1] == nil then
|
|
coroutine.yield()
|
|
else
|
|
hpv.triggerEvent("all", event[1], table.unpack(event,2))
|
|
coroutine.yield()
|
|
end
|
|
end
|
|
end, "eventHandler")
|
|
|
|
while true do
|
|
coroutine.yield()
|
|
end
|
|
end)
|
|
|
|
term.print("Goodbye :)") |