Thanks for this.
I'm a little bit wary of adding yet another variable to track "alt" state, but it may be the most straightforward way to deal with it.
Anyway, I spent some time trying to understand the current state of affairs, and ran into another bit of (probably unrelated to your issue) weirdness in this area:
Note this is without the patch, on elph180
Running a chdkptp script which peeks the relevant values, camera not in alt:
kbd_blocked:1
camera_info.state.gui_mode:3 (GUI_MODE_SCRIPT)
camera_info.state.gui_mode_none:0
camera_info.state.gui_mode_alt:0
With cam in alt, set manually on the camera before running
kbd_blocked:1
camera_info.state.gui_mode:1 (GUI_MODE_ALT)
camera_info.state.gui_mode_none:0
camera_info.state.gui_mode_alt:1
The values are the same with a 500ms sleep before peeking, so it's not just a matter of spytask not updating state yet.
In other words, when the camera is already in "alt", running a PTP script doesn't go to GUI_MODE_SCRIPT, instead, it stays in GUI_MODE_ALT, which is not actually the same. This can be verified by running a long running script like
=for i=1,1000 do sleep(10) end
and interrupting it with the shutter. If the camera was not in alt, you get *interrupted*. If it was, you get the default script, and likely memory corruption, because it doesn't kill / clean up the running script.
While this doesn't seem directly connected to your issue, in the first case (camera not in alt at PTP call), it seems like a second script run before spytask responded to the exit_alt should see camera_info.state.gui_mode_alt == 0, since it would still be in script mode. I could very easily be missing something though
It might be possible for gui_activate_alt_mode to run between when lua_script_start finishes and when script_stack_start sets camera_info.state.state_kbd_script_run
script_end can also set the gui handler directly, but I think that only happens in the GUI case.