made modload more failsafe

This commit is contained in:
Ponali
2025-10-11 10:31:31 +02:00
parent 1798d63864
commit 62a2466c5e
+84 -49
View File
@@ -3,63 +3,98 @@ local fs = require("filesystem")
local modulePath = "/halyde/kernel/modules" local modulePath = "/halyde/kernel/modules"
local moduleList = assert(fs.list(modulePath)) if not (fs.exists(modulePath) or fs.isDirectory(modulePath)) then
return log.kernel.warn(
string.format("Module directory (%s) does not exist and/or has been detected as a file - skipping", modulePath)
)
end
local moduleList, err = fs.list(modulePath)
if not moduleList then
return log.kernel.warn(
string.format("Could not get list of modules (from %s): %s", modulePath, tostring(err or "unknown error"))
)
end
local modules = {} local modules = {}
local moduleTypes = {} local moduleTypes = {}
local function loadModule(modName) local function loadModule(modName)
local moduleData = modules[modName] local moduleData = modules[modName]
table.remove(moduleList, table.find(moduleList, modName)) table.remove(moduleList, table.find(moduleList, modName))
if not moduleData then if not moduleData then
log.kernel.warn(string.format("[modload: %s] Could not find module data.", modName)) log.kernel.warn(string.format("[modload: %s] Could not find module data.", modName))
return return
end end
if not moduleData.check() then if not moduleData.check() then
log.kernel.info(string.format("[modload: %s] Module not ready - skipping", modName)) log.kernel.info(string.format("[modload: %s] Module not ready - skipping", modName))
return return
end end
if moduleData.dependencies then if moduleData.dependencies then
for _, dependency in pairs(moduleData.dependencies) do for _, dependency in pairs(moduleData.dependencies) do
if table.find(moduleList, dependency) then if table.find(moduleList, dependency) then
loadModule(dependency) loadModule(dependency)
elseif table.find(moduleList, dependency .. ".lua") then elseif table.find(moduleList, dependency .. ".lua") then
loadModule(dependency .. ".lua") loadModule(dependency .. ".lua")
else else
for typeLookupDrvName, typeLookupDrvType in pairs(moduleTypes) do for typeLookupDrvName, typeLookupDrvType in pairs(moduleTypes) do
if typeLookupDrvType == dependency then if typeLookupDrvType == dependency then
loadModule(typeLookupDrvName) loadModule(typeLookupDrvName)
-- Don't break, because there can be multiple modules of the correct type -- Don't break, because there can be multiple modules of the correct type
end end
end end
end end
end end
end end
--print(modName) --print(modName)
log.kernel.info(string.format("[modload: %s] Loading module", modName)) log.kernel.info(string.format("[modload: %s] Loading module", modName))
if moduleData.init then -- I have no idea why this would not exist, but it's a failsafe if moduleData.init then -- I have no idea why this would not exist, but it's a failsafe
moduleData.init() moduleData.init()
end end
end end
for _, modName in pairs(moduleList) do -- Get all the module types for _, modName in pairs(moduleList) do -- Get all the module types
log.kernel.info(string.format("[modload: %s] Getting data from module", modName)) log.kernel.info(string.format("[modload: %s] Getting data from module", modName))
local moduleData = require(fs.concat(modulePath, modName)) -- TODO: Make this not actually throw an error, rather put something in the log and move on local moduleData
if type(moduleData) ~= "table" then local status, err = pcall(function()
log.kernel.error( moduleData = require(fs.concat(modulePath, modName)) -- TODO: Make this not actually throw an error, rather put something in the log and move on
string.format("[modload: %s] Module returned invalid type (%s) - skipping", modName, type(moduleData)) end)
) if not status then
goto continue log.kernel.error(
end string.format(
modules[modName] = moduleData "[modload: %s] Module returned error while getting data: %s",
if moduleData.type then modName,
--print(moduleData.type) tostring(err or "unknown error")
moduleTypes[modName] = moduleData.type -- Not the other way around because there can be multiple modules of the same type, but there can't be multiple entries with the same key )
end )
::continue:: goto continue
end
if type(moduleData) ~= "table" then
log.kernel.error(
string.format("[modload: %s] Module returned invalid type (%s) - skipping", modName, type(moduleData))
)
goto continue
end
if type(moduleData.check) ~= "function" then
log.kernel.error(string.format('[modload: %s] Module doesn\'t contain a "check" function', modName))
goto continue
end
if type(moduleData.init) ~= "function" then
log.kernel.error(string.format('[modload: %s] Module doesn\'t contain an "init" function', modName))
goto continue
end
if type(moduleData.exit) ~= "function" then
log.kernel.error(string.format('[modload: %s] Module doesn\'t contain an "exit" function', modName))
goto continue
end
modules[modName] = moduleData
if moduleData.type then
--print(moduleData.type)
moduleTypes[modName] = moduleData.type -- Not the other way around because there can be multiple modules of the same type, but there can't be multiple entries with the same key
end
::continue::
end end
while moduleList[1] do while moduleList[1] do
if moduleList[1]:sub(-1, -1) ~= "/" then -- Check if it's not a directory. If it is, it might be module config if moduleList[1]:sub(-1, -1) ~= "/" then -- Check if it's not a directory. If it is, it might be module config
loadModule(moduleList[1]) loadModule(moduleList[1])
end end
end end