From: Mark Kettenis Subject: Re: Booting 8.0 on qemu-system-sparc64 fails Unimplemented service set-symbol-lookup To: Ted Bullock Cc: david@stanaway.net, sparc@openbsd.org, tech@openbsd.org Date: Wed, 04 Nov 2026 07:48:21 +0100 > From: Ted Bullock > Date: Tue, 03 Nov 2026 23:19:04 -0600 This will have to be tested on a wider range of real hardware. > Hi David and tech@ > > Ok, so the OpenBSD kernel and bootloader have a defect according to the > open firmware specification that stops openbsd from booting with sparc on > qemu with its bundled firmware. We’re requesting zero return values and leaving > no space for the catch result and ending up clobbered with overwritten memory. > > The openboot firmware is more graceful for our request than openbios > which is why we don't see this on physical sun machines. > > Anyway, this shows up a few times for the call-method firmware operation, > it's supposed to be able to return the extra value and we are getting > hit by that. > > The following patch fixes the kernel and the bootloader so they follow > the Open Firmware Client Interface Developer’s Guide. > > Page 26 has the rule: > The arguments N_args and N_returns specify the number of calling arguments > and return values; they must agree with the number of arguments and > return values expected by the particular service. > > and Page 30 describes "call-method" > OUT: catch-result, stack-result1, ... , stack-resultQ > > Pops the result returned by catch into catch-result. > > If that result is zero, pops up to N_returns-1 items from the Forth data > stack into the returned values portion of the argument array, with > stack_result1 corresponding to the top of the stack. > > Anyway, my Sun Blade boots without this patch. With the patch, QEMU boots > with its shipped BIOS. > > --- a/sys/arch/sparc64/sparc64/ofw_machdep.c > +++ b/sys/arch/sparc64/sparc64/ofw_machdep.c > @@ -260,6 +260,7 @@ > cell_t ihandle; > cell_t len; > cell_t vaddr; > + cell_t status; > } args; > > if (mmuh == -1 && ((mmuh = get_mmu_handle()) == -1)) { > @@ -268,7 +269,7 @@ > } > args.name = ADR2CELL("call-method"); > args.nargs = 4; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("release"); > args.ihandle = HDL2CELL(mmuh); > args.vaddr = ADR2CELL(vaddr); > @@ -293,6 +294,7 @@ > cell_t ihandle; > cell_t len; > cell_t vaddr; > + cell_t status; > } args; > > if (mmuh == -1 && ((mmuh = get_mmu_handle()) == -1)) { > @@ -301,7 +303,7 @@ > } > args.name = ADR2CELL("call-method"); > args.nargs = 4; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("unmap"); > args.ihandle = HDL2CELL(mmuh); > args.vaddr = ADR2CELL(vaddr); > @@ -328,6 +330,7 @@ > cell_t vaddr; > cell_t phys_hi; > cell_t phys_lo; > + cell_t status; > } args; > > if (mmuh == -1 && ((mmuh = get_mmu_handle()) == -1)) { > @@ -336,7 +339,7 @@ > } > args.name = ADR2CELL("call-method"); > args.nargs = 7; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("map"); > args.ihandle = HDL2CELL(mmuh); > args.mode = mode; > @@ -443,6 +446,7 @@ > cell_t len; > cell_t phys_hi; > cell_t phys_lo; > + cell_t status; > } args; > > if (memh == -1 && ((memh = get_memory_handle()) == -1)) { > @@ -451,7 +455,7 @@ > } > args.name = ADR2CELL("call-method"); > args.nargs = 5; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("release"); > args.ihandle = HDL2CELL(memh); > args.len = len; > > --- a/sys/arch/sparc64/stand/ofwboot/Locore.c > +++ b/sys/arch/sparc64/stand/ofwboot/Locore.c > @@ -420,11 +420,12 @@ > cell_t ihandle; > cell_t len; > cell_t vaddr; > + cell_t status; > } args; > > args.name = ADR2CELL("call-method"); > args.nargs = 4; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("release"); > args.ihandle = HDL2CELL(mmuh); > args.vaddr = ADR2CELL(vaddr); > @@ -452,11 +453,12 @@ > cell_t vaddr; > cell_t paddr_hi; > cell_t paddr_lo; > + cell_t status; > } args; > > args.name = ADR2CELL("call-method"); > args.nargs = 7; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("map"); > args.ihandle = HDL2CELL(mmuh); > args.mode = mode; > @@ -519,11 +521,12 @@ > cell_t len; > cell_t phys_hi; > cell_t phys_lo; > + cell_t status; > } args; > > args.name = ADR2CELL("call-method"); > args.nargs = 5; > - args.nreturns = 0; > + args.nreturns = 1; > args.method = ADR2CELL("release"); > args.ihandle = HDL2CELL(memh); > args.len = len; > >