Updated error handler

This commit is contained in:
MaddoScientisto 2024-05-01 10:26:14 +02:00
commit c2138979f6

View file

@ -2,7 +2,7 @@
--
-- by kira
--
-- version 0.0.4
-- version 0.0.6
--
-- an interactive error screen for picotron.
-- on error, shows the stack, local variables,
@ -41,6 +41,19 @@
--
-- ## version history
--
-- version 0.0.6
-- - on error:
-- - show cursor
-- - make window resizable
-- - automatically adjust layout to window size
-- - support yielding (since fetch sometimes yields)
--
-- version 0.0.5
--
-- - future proofing: gracefully handle when
-- various parts of the `debug` module aren't
-- available
--
-- version 0.0.4
--
-- - also catch errors in `_init`
@ -195,9 +208,6 @@ local source_lines = {}
---- main events ---------------------------------
local W = 480
local H = 270
local function rebuild ()
-- rebuild stack frame info
stack_frames = {}
@ -232,33 +242,45 @@ local function rebuild ()
-- rebuild variables
do
local local_index = 1
repeat
local name, value = debug.getlocal (error_thread, frame.depth, local_index)
if name then
if name ~= '(temporary)' then
table.insert (variables, {
key = name,
value = value,
})
end
local_index = local_index + 1
end
until not name
local info = debug.getinfo (error_thread, frame.depth)
if info and info.func then
local upvalue_index = 1
if debug.getlocal then
local local_index = 1
repeat
local name, value = debug.getupvalue (info.func, upvalue_index)
local name, value = debug.getlocal (error_thread, frame.depth, local_index)
if name then
table.insert (variables, {
key = name,
value = value,
})
upvalue_index = upvalue_index + 1
if name ~= '(temporary)' then
table.insert (variables, {
key = name,
value = value,
})
end
local_index = local_index + 1
end
until not name
else
table.insert (variables, {
error = 'no debug.getlocal, can\'t show locals'
})
end
if debug.getupvalue then
local info = debug.getinfo (error_thread, frame.depth)
if info and info.func then
local upvalue_index = 1
repeat
local name, value = debug.getupvalue (info.func, upvalue_index)
if name then
table.insert (variables, {
key = name,
value = value,
})
upvalue_index = upvalue_index + 1
end
until not name
end
else
table.insert (variables, {
error = 'no debug.getupvalue, can\'t show upvalues'
})
end
end
@ -328,6 +350,9 @@ local function error_update ()
end
local function error_draw ()
local W = get_display():width()
local H = get_display():height()
local prefix = use_small_font and '\014' or ''
local font_height = (use_small_font and 6 or 11)
local mx, my = mouse()
@ -418,9 +443,13 @@ local function error_draw ()
variable_count = variable_count + 1
local hovered = variable == last_hovered_variable
local y_before = y
print_horizontal (indent .. variable.key, hovered and 7 or 6)
print_horizontal (': ', variable == last_hovered_variable and 7 or 5)
print_line (safe_tostring(variable.value))
if variable.error then
print_line (' ' .. variable.error, 8)
else
print_horizontal (indent .. variable.key, hovered and 7 or 6)
print_horizontal (': ', variable == last_hovered_variable and 7 or 5)
print_line (safe_tostring(variable.value))
end
if over_section and type (variable.value) == 'table' then
if mx >= 0 and mx < W/2 and my >= y_before and my < y then
@ -459,6 +488,10 @@ end
local function reset ()
-- based on reset() from /system/lib/head.lua
-- see that fn for info
window {
cursor = 1,
resizable = true,
}
note ()
-- picotron segfaults if we call clip() during init
if init_done then
@ -511,7 +544,12 @@ local user_update = rawget (_G, '_update')
local user_draw = rawget (_G, '_draw')
assert (user_draw and user_update,
'please include install_error_handler after defining both _update and _draw')
'please include error_explorer after defining both _update and _draw')
if not rawget (_G, 'debug') or not debug.traceback or not debug.getinfo then
printh 'error explorer: debug module not available, error explorer will be disabled'
return
end
local function call_error_event (fn, ...)
-- if there's an error in our update or draw, throw the
@ -527,8 +565,9 @@ local function call_protected (fn)
-- for picotron compatibility
local thread = cocreate (fn)
local success, message = coresume(thread)
if costatus (thread) ~= 'dead' then
call_error_event (on_error, thread, 'setup_error_display.lua: _update and _draw shouldn\'t yield')
while costatus (thread) ~= 'dead' do
yield ()
success, message = coresume (thread)
end
if not success then
call_error_event (on_error, thread, message)