[OpenBIOS] Even more findings to report about booting Mac OS 9

Segher Boessenkool segher at kernel.crashing.org
Sun Apr 17 03:14:41 CEST 2016

On Sat, Apr 16, 2016 at 08:09:47PM -0400, Tarl Neustaedter wrote:
> On 2016-Apr-16 19:17 , Programmingkid wrote:
> > I added some code to the bootinfo_init_program() function in bootinfo_load.c file that changes all control characters to '\n'. This made Mac OS 9 boot. But when I changed the control characters to a single space, Mac OS 9 failed to boot. This seems strange to me. The space character is the ultimate whitespace character, so why would it fail when '\n' succeeds? My only guess right now is a bug with one of the words in Forth.
> Well, changing end-of-line to space will probably fail for the following
> standard words (doing a search through IEEE 1275 for EOL):
> \
> dev
> "
> parse
> load
> help
> setenv
> devalias
> boot
> set-default
> printenv
> The last seven are supposed to be interactive commands, so no surprise
> they need an EOL. "dev" is supposed to be as well, but it's too-widely
> used in code (they should be using '" /" find-device' instead of 'dev
> /', but poor programming isn't limited to C language). It's rare to see
> a quoted string ended by end-of-line, but I have run into it.

Yes.  Anything that calls PARSE (or WORD or PARSE-WORD or NAME or whatever
similar words you have) depends on this.  That is a much longer list than
what you found, for example, also  (  is in that list.

EVALUATE makes its whole argument string the input buffer, as one string.
It does not handle multiple lines.  If you want to use it to handle the
boot script, you should break things into lines yourself.

> I suspect that as Mark was suggesting, the CR vs LF is a red herring.
> The issue is likely to be what happens to the return stack between
> commands - the forth interpreter might trash the return stack between
> commands - it could well be that in the process of parsing strings from
> the boot code, it's resetting the return stack, and that's where we're
> getting tripped up. Maybe some parsing code goes through a different
> path for CR vs LF, for example. Apple's Forth code is known to take
> advantage of Apple's interpreter's quirks, to the degree that plug-in
> card manufacturers had to produce different code for Sun, IBM and Apple
> systems.

Between words is the first part of the problem; it's not very hard to
make you parser loop play tricks so you can mess with the return stack
as well.

But the OS9 boot code also messes with the return stack between _lines_.
And allowing that is not feasible.

The usual solution is to implement a separate R stack for use in
interpretation mode (just an array in Forth, not some magic system-provided
something).  The only limitation is that you cannot put something in the
R stack in interpret mode and then access it in compile mode (or the other
way around).  This isn't a problem in practice.

> On the other hand, I can't think of much bad that will happen by
> replacing all CR (0x0D) with LF (0x0A),

Yeah.  Many systems use the "parsing 20 means parsing anything <= 20",
i.e., parsing a space allows all cosntrol chars as well.  I think that
is an OF requirement even?  Then (on code where the line delimiter is
0d 0a and there are no other 0d or 0a in the file) you just get an extra
blank line after every line, which usually is harmless.

> One possible solution; take the boot-script code, and rather than
> interpret it directly, try compiling it.

That does not work.  The OS9 bootscript contains many definitions as well.
Not just colon definitions.

In summary, the two things you need:

-- Parse the bootscript line by line.
-- Have a separate interpretation mode R stack.


More information about the OpenBIOS mailing list