Recent Doors CSE bug reports revealed that the method of catching program execution from the homescreen was overzealous. Specifically, any homescreen line with "prgmXXX" in it was collapsed to simply run prgmXXX, and not execute any of the other functions specified in that line. Looking back at my code, I borrowed very heavily from BrandonW's Noshell hook code, using his code to find the program name in the line with minimal modifications. I'm refining my approach to execute homescreen programs under two conditions:
Since very few community members have messed with Class 2 functions, the documentation on WikiTI is sparse. My questions:
My biggest concerns so far are (a) question 1 above, and (b) whether I'm missing some important detail about why catching only these two cases is not enough. Thanks in advance.
Edit: I found that although my solution does work, it doesn't help with running Archived programs. The OS checks if a program is Archived before invoking the ParserHook for something like 1->A:prgmXXX, so I'm considering solutions where I replace all of the prgm tokens in a homescreen line with some other Class 1 command at the beginning of parsing. BrandonW asked why I don't just intercept prgm, and I believe the answer is that the ParserHook isn't invoked on the prgm token.
- When prgmXXX appears as a command by itself, the ParserHook is triggered with a=0, parseVar=[5|6]"NAME". To avoid prematurely triggering my ParserHook when a whole line is parsed, I abort if the program name is "!" or "#".
- When the Asm( command appears in a line (apparently a Class 2 function, so a=2 and bc=$5D01), I run the specified program if the token immediately after Asm( is prgm. To find the program name, I copy characters until I reach [^A-Z0-9] or the end of the line.
Since very few community members have messed with Class 2 functions, the documentation on WikiTI is sparse. My questions:
- Why is Asm( equivalent to bc=$5D01 instead of $BB6A or something else logical? Is this in fact Asm(?
- WikiTI is vague on what "If you return NZ, the parser will continue execution from where you left off" means. I discovered that if you modify curPC, begPC, and endPC, you need to restore them. "Where you left off" is determined by curPC, so I put curPC right after the Asm() command.
- The OS does not push and pop hl around the ParserHook call, at least on TI-84+CSE OS 4.0, and it uses it right after the ParserHook call if the hook returns z (ie, continue normally). Therefore, ParserHooks that catch Class 2 functions must preserve hl if they're planning to return z. This does not apply to Class 0 invocations of the ParserHook, it seems.
My biggest concerns so far are (a) question 1 above, and (b) whether I'm missing some important detail about why catching only these two cases is not enough. Thanks in advance.
Edit: I found that although my solution does work, it doesn't help with running Archived programs. The OS checks if a program is Archived before invoking the ParserHook for something like 1->A:prgmXXX, so I'm considering solutions where I replace all of the prgm tokens in a homescreen line with some other Class 1 command at the beginning of parsing. BrandonW asked why I don't just intercept prgm, and I believe the answer is that the ParserHook isn't invoked on the prgm token.