7400,7410,7450 cpus vector have wrong exception prefix at reset I have a proprietary ROM implementing system calls that are executed via the 'SC' instruction. I use qemu-0.14.1, qemu-system-ppc -M prep -cpu $CPU -bios my_bios -kernel my_kernel That works fine on a 604 (CPU=0x00040103) - but does not on an emulated 7400 (CPU=0x000c0209) or 7450 (CPU=0x80000201). I found that the emulator jumps to 0x00000c00 instead of 0xfff00c00. Probably this is due to a wrong setting in target-ppc/translate_init.c: init_excp_604() correctly sets env->hreset_vector=0xfff00000UL; but init_excp_7400() says env->hreset_vector=0x00000000UL; which seems wrong. (the 7400 manual says a hard-reset jumps initializes the prefix to 0xfff00000.) Likewise, init_excp_7450() (and probably other, related CPUs) are wrong. Indeed, when I change the value in init_excp_7400() to 0xfff00000UL then everything works as expected for me. Hi, Am 16.07.2011 um 23:49 schrieb till: > I have a proprietary ROM implementing system calls that are executed > via > the 'SC' instruction. > > I use qemu-0.14.1, > > qemu-system-ppc -M prep -cpu $CPU -bios my_bios -kernel my_kernel > > That works fine on a 604 (CPU=0x00040103) - but does not on an > emulated 7400 (CPU=0x000c0209) or 7450 (CPU=0x80000201). I found > that the emulator jumps to 0x00000c00 instead of 0xfff00c00. > Probably this is due to a wrong setting in target-ppc/ > translate_init.c: > > init_excp_604() correctly sets env->hreset_vector=0xfff00000UL; > > but > > init_excp_7400() says env->hreset_vector=0x00000000UL; > > which seems wrong. (the 7400 manual says a hard-reset jumps > initializes the > prefix to 0xfff00000.) Do you have a link to a spec saying so? Should be trivial to change then. > Likewise, init_excp_7450() (and probably other, related CPUs) are > wrong. > > Indeed, when I change the value in init_excp_7400() to 0xfff00000UL > then > everything works as expected for me. > > ** Affects: qemu > Importance: Undecided > Status: New > Bug description: > I have a proprietary ROM implementing system calls that are executed > via the 'SC' instruction. > > I use qemu-0.14.1, > > qemu-system-ppc -M prep -cpu $CPU -bios my_bios -kernel my_kernel We are currently in the process of revamping the PReP machine you are using above. Is your BIOS available publicly so that we can test we don't break anything for you? Andreas On 18.07.2011, at 00:34, Andreas Färber wrote: > Hi, > > Am 16.07.2011 um 23:49 schrieb till: > >> I have a proprietary ROM implementing system calls that are executed via >> the 'SC' instruction. >> >> I use qemu-0.14.1, >> >> qemu-system-ppc -M prep -cpu $CPU -bios my_bios -kernel my_kernel >> >> That works fine on a 604 (CPU=0x00040103) - but does not on an emulated 7400 (CPU=0x000c0209) or 7450 (CPU=0x80000201). I found that the emulator jumps to 0x00000c00 instead of 0xfff00c00. >> Probably this is due to a wrong setting in target-ppc/translate_init.c: >> >> init_excp_604() correctly sets env->hreset_vector=0xfff00000UL; >> >> but >> >> init_excp_7400() says env->hreset_vector=0x00000000UL; >> >> which seems wrong. (the 7400 manual says a hard-reset jumps initializes the >> prefix to 0xfff00000.) > > Do you have a link to a spec saying so? Should be trivial to change then. According to MPC7450UM.pdf: MSR Bit Settings Bit: 25 Name: IP Exception prefix. The setting of this bit specifies whether an exception vector offset is prepended with Fs or 0s. In the following description, nnnnn is the offset of the exception. 0 Exceptions are vectored to the physical address 0x000n_nnnn. 1 Exceptions are vectored to the physical address 0xFFFn_nnnn. [...] 9.9.1 Reset Inputs The MPC7450 has two reset inputs, described as follows: • HRESET (hard reset)—The HRESET signal is used for power-on reset sequences, or for situations in which the MPC7450 must go through the entire cold start sequence of internal hardware initialization. The MPC7450 will initiate burst transactions after power-on reset in 60x bus mode. • SRESET (soft reset)—The soft reset input provides warm reset capability. This input can be used to avoid forcing the MPC7450 to complete the cold start sequence. When either reset input negates, the processor attempts to fetch code from the system reset exception vector. The vector is located at offset 0x00100 from the exception prefix (MSR[IP]). ----> The MSR[IP] bit is set when HRESET negates. So the correct implementation would be to set hreset_vector to 0xfff00000, but also set MSR_IP and clear hreset_vector when MSR_IP gets modified. I'll happily take patches :). Alex Google for MPC7450UM.pdf and MPC7410UM.pdf. These two documents cover the 7441, 7445, 7451, 7455, 7457, 7447, 7448 and the 7410 and 7400 CPUs, respectively. For all these, Alex' description applies. However, (and I made a mistake in my original post), the setting affected is env->hreset_excp_prefix = 0xfff00000UL; in addition, hreset_vector should be: env->hreset_vector = 0x00000100UL; NOTE - I believe the other points raised by Alex (initialize MSR[IP] -- which BTW is called MSR_EP in qemu -- and switching the exception prefix when MSR[IP] is changed) are already correctly handled, see: target-ppc/helper.c: cpu_reset() target-ppc/helper-hreg.h: hreg_store_msr() Should I post a patch to the mailing-list? Hi Andreas. I posted a reply to the bug database. Regarding my 'bios' - it is really nothing. I need it to boot RTEMS. It just mocks up a minimal residual and jumps to the kernel load address. You can take a look at http://www.rtems.org/viewvc/rtems/c/src/lib/libbsp/powerpc/shared/bootloader/ The stuff that goes into the dummy 'bios' is qemu_fakerom.S and qemu_fakeres.c Regards - Till On 07/17/2011 05:34 PM, Andreas Färber wrote: > Hi, > > Am 16.07.2011 um 23:49 schrieb till: > >> I have a proprietary ROM implementing system calls that are executed >> via >> the 'SC' instruction. >> >> I use qemu-0.14.1, >> >> qemu-system-ppc -M prep -cpu $CPU -bios my_bios -kernel my_kernel >> >> That works fine on a 604 (CPU=0x00040103) - but does not on an >> emulated 7400 (CPU=0x000c0209) or 7450 (CPU=0x80000201). I found >> that the emulator jumps to 0x00000c00 instead of 0xfff00c00. >> Probably this is due to a wrong setting in target-ppc/ >> translate_init.c: >> >> init_excp_604() correctly sets env->hreset_vector=0xfff00000UL; >> >> but >> >> init_excp_7400() says env->hreset_vector=0x00000000UL; >> >> which seems wrong. (the 7400 manual says a hard-reset jumps >> initializes the >> prefix to 0xfff00000.) > Do you have a link to a spec saying so? Should be trivial to change > then. > >> Likewise, init_excp_7450() (and probably other, related CPUs) are >> wrong. >> >> Indeed, when I change the value in init_excp_7400() to 0xfff00000UL >> then >> everything works as expected for me. >> >> ** Affects: qemu >> Importance: Undecided >> Status: New >> Bug description: >> I have a proprietary ROM implementing system calls that are executed >> via the 'SC' instruction. >> >> I use qemu-0.14.1, >> >> qemu-system-ppc -M prep -cpu $CPU -bios my_bios -kernel my_kernel > We are currently in the process of revamping the PReP machine you are > using above. Is your BIOS available publicly so that we can test we > don't break anything for you? > > Andreas > Looking through old bug tickets... can you still reproduce this issue with the latest version of QEMU? Or could we close this ticket nowadays? I no longer have the test readily available. So I tried to print the initial MSR and IP register contents from the QEMU monitor: qemu-system-ppc -machine none -cpu 7400 -S -monitor stdio QEMU 5.0.93 monitor - type 'help' for more information (qemu) info registers NIP 00000000 LR 00000000 CTR 00000000 XER 00000000 CPU#0 MSR 00000000 HID0 00000000 HF 00000000 iidx 0 didx 0 Segmentation fault (core dumped) Unfortunately this lets qemu (tried 2.11.1(Debian 1:2.11+dfsg-1ubuntu7.29) as well as 5.1.0-rc3) segfault; apparently the time-base is not initialized but still accessed when -machine == none. Yet another bug, it seems. The NIP and MSR seem wrong, however. I can generate an empty ppc_rom.bin and fool a prep machine under 2.11.1: till@tillp1 $ ls -l empty.bin -rw-r--r-- 1 till till 0 Aug 8 12:03 empty.bin till@tillp1 $ qemu-system-ppc -bios ./empty.bin -cpu 7400 -machine prep -S -monitor stdio QEMU 2.11.1 monitor - type 'help' for more information (qemu) info registers NIP fff00100 LR 00000000 CTR 00000000 XER 00000000 CPU#0 MSR 00000040 HID0 00000000 HF 00000000 iidx 3 didx 3 Here, the issue is fixed! Apparently it is fixed for the 'prep' machine but not 'none'. Unfortunately 'prep' is gone from 5.3.0 and 'none' is buggy; wait - it seems I can emulate 'prep' with '40p': till@tillp1 $ build/ppc-softmmu/qemu-system-ppc -machine 40p -cpu 7400 -S -monitor stdio QEMU 5.0.93 monitor - type 'help' for more information (qemu) info registers NIP fff00100 LR 00000000 CTR 00000000 XER 00000000 CPU#0 MSR 00000040 HID0 00000000 HF 00000000 iidx 3 didx 3 This looks good, so I suppose it is OK to close this bug. Ok, thanks for checking! I'll keep the bug open, though, in case someone wants to have a look at the segfault with the "none" machine. Please don't close ticket if there's a known problem just to at least document there's a problem. Is this a CPU feature or board specific? Doesn't these CPUs have some way to select the exception vectors base and could that be set wrong? I've also seen some problems with these CPUs but last time I asked nobody answered: https://lists.nongnu.org/archive/html/qemu-ppc/2020-03/msg00292.html Could this bug be related to that? Yes, it is a CPU feature, and yes you can select the exception vector prefix with the MSR[IP] bit which should be set by a hardware reset. The initial value seems wrong in qemu but that seems to fixed by the machine-specific initialization. The 'none' machine, however, just uses generic code and does not do anything PPC-specific. This means that - the MSR and probably other registers, too, are not initialized to what the hardware documentation specifies as reset values. - the time-base is not initialized at all (and this leads to a segfault when you start the ppc 'none' machine) - probably other things are not properly initialized. I wonder, e.g., about the MMU... It seems that all registers are simply initialized to zero. Then, there seems to be a 'reset' function which initializes the registers to the proper reset values (well - sort of bug 812398 reports that HID0 is not properly initialized by some CPU flavours). However, that reset function is not executed by the 'none' machine initialization.... This is an automated cleanup. This bug report has been moved to QEMU's new bug tracker on gitlab.com and thus gets marked as 'expired' now. Please continue with the discussion here: https://gitlab.com/qemu-project/qemu/-/issues/85