Emulator Issues #12498
openSyobon Action Wii (Homebrew) Doesn't Work
0%
Description
Game Name?
Syobon Action Wii
MD5 Hash? (right click the game in the game list, Properties, Verify tab, Verify Integrity button)
AC479A918A3C3F8F5E973CEC6B220962
What's the problem? Describe what went wrong.
Opening the game just results on a black screen and nothing can be done.
What steps will reproduce the problem?
1.- Open the Syobon Action Wii .dol
Is the issue present in the latest development version? For future reference, please also write down the version number of the latest development version.
Yes, 5.0-14081
Is the issue present in the latest stable version?
Yes, Dolphin 5.0
What are your PC specifications? (CPU, GPU, Operating System, more)
Intel Core i5-10400 CPU @ 4.00GHz
UHD IntelĀ® 630
Windows 10 Pro x64
Files
Updated by JMC4789 over 3 years ago
Is this a free homebrew? If so can you link to where we can get it?
Updated by Clector over 3 years ago
Yes, it is.
There's the link: https://wii.brewology.com/downloads/download.php?id=10491&mcid=3
Updated by sepalani over 3 years ago
Here is the official website with the source code
Updated by sepalani over 3 years ago
- File syobon-action-wii.7z syobon-action-wii.7z added
The homebrew can run using Emulated CPU Clock Override
at 10%
. It needs DSP LLE to play audio, otherwise, it runs properly.
It sounds like a DMA issue to me, maybe like https://dolp.in/i9509
The game keeps spamming in the log: Audio DMA configured: 128 blocks from 0x0039aca0
25:27:480 Core\HW\DSP.cpp:391 I[AI]: Audio DMA configured: 128 blocks from 0x00398ca0
25:27:480 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00af (0x0000)
25:27:482 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00ee (0x0000)
25:27:486 Core\HW\DSP.cpp:391 I[AI]: Audio DMA configured: 128 blocks from 0x0039aca0
25:27:486 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00af (0x0000)
25:27:489 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00ee (0x0000)
25:27:510 Core\HW\DSP.cpp:391 I[AI]: Audio DMA configured: 128 blocks from 0x00398ca0
25:27:510 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00af (0x0000)
25:27:514 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00ee (0x0000)
25:27:531 Core\HW\DSP.cpp:391 I[AI]: Audio DMA configured: 128 blocks from 0x0039aca0
The game doesn't crash per se but is interrupted (during a setjmp call, IIRC) in a function which loads PNG and doesn't come back to it.
It doesn't occur with the version I compiled from source which is working without DMA issues:
33:36:922 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00af (0x0000)
33:36:925 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00ee (0x0000)
33:36:943 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00af (0x0000)
33:36:946 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00ee (0x0000)
33:36:965 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00af (0x0000)
33:36:965 Core\DSP\DSPHWInterface.cpp:101 W[DSPLLE]: Unknown Interrupt Request pc=0x00ee (0x0000)
Updated by sepalani over 3 years ago
After digging more into the issue, I managed to find why the game doesn't resume. Basically, the audio interrupt is happening too quickly:
This audio interrupt is also preventing Wii/Hollywood IRQs to be processed by libogc:
- IRQ priority: https://github.com/devkitPro/libogc/blob/master/libogc/irq.c#L74
- https://github.com/devkitPro/libogc/blob/master/libogc/irq.c#L254
The WPAD's IOS_IoctvAsync
can't be processed due to that. It was initiated by WPAD_Init
:
// Functions called from WPAD_Init
WPAD_Init
BTE_Init
physbusif_init
__usb_open
__issue_bulkread
__readbulkdataCB
// Infinite async WPAD loop handled by __readbulkdataCB
__issue_bulkread
USB_ReadBlkMsgAsync(__readbulkdataCB)
__usb_interrupt_bulk_message
IOS_IoctlvAsync(__usbv0_messageCB)
Now, I need to find precisely what makes Dolphin too fast:
- It can be specific instruction timing (for instance, mtspr/mfspr used in epilog/prolog from the exception handler)
- The interrupt timing
- Something else?
I hardware tested the interrupt timing and Dolphin's timing is really close to what the hardware does. Unless there are special cases where its timing can be delayed/canceled (still have to hwtest that), I doubt that's the root cause.
I'll investigate more to see if I can find anything interesting.
Updated by sepalani over 3 years ago
I think I have all pieces of the puzzle, now.
Dolphin point of view¶
- Syobon Action boots up and its
main
function calls some functions that will produce interrupts later on:
WPAD_Init
ASND_Init
's AUDIO_StartDMA
- The game is stuck on a floating-point instruction with FPU disabled (lazy FP context switch) at
80052644 stfdu f14, 0x0008 (r3)
-
It raises an
FPU unavailable
exception and its handler re-enable FP. -
However, while resuming at
80052644
the FP instruction isn't processed as the AI interrupt occurs
The one generated by
AUDIO_StartDMA
- It goes through the IRQ handler
- Then, the IRQ dispatcher
- Said dispatcher that calls the audio's DMA callback
- The Audio DMA callback
- calls AUDIO_StartDMA
- exits early as
static vs32 global_pause = 1
- Indeed, the game's
ogg_player_thread
'sASND_Pause(0)
hasn't been called yet
-
Upon exiting the IRQ handler, FP is disabled again
-
Execution resumes at
80052644
80052644 stfdu f14, 0x0008 (r3)
and raises (see 3.)FPU unavailable
exception
- Rinse and repeat from
3.
Summary¶
Unless I did something wrong, here is why the game can't start properly:
- The execution is stuck on a floating point instruction.
- The AI interrupt is the only one processed.
- The FP exception handler takes enough time for the next AI interrupt to be generated.
- It seems more like an execution timing issue than an audio timing issue.
What I tried¶
I created a bunch of hardware tests to check various cases such as audio/interrupt timing and FP exception.
Based on them, I think:
- Dolphin's DMA timing should be good enough
- It seems to happen on real hardware but with another timing (I can't check where it's stuck, though)
- I used
AUDIO_StartDMA
's AI interrupt, - I forced FP exception in a loop with something like this:
- I used
float volatile dummy = 1.0f;
for (u32 i = 0; i < 5; i += 1)
{
// Trigger FPU unavailable exception
_CPU_FPR_Disable();
dummy *= 2.0f;
}
I exhausted most of the things I could think of. I might, at a later point, try to improve MMIO timings to be closer to real hardware. Delaying the audio interrupts (or using CPU clock overriding) allows the FP instructions to be executed properly.
Updated by pokechu22 over 2 years ago
- Related to Emulator Issues #12799: Rick Dangerous Wii - Doesn't Boot added
Updated by pokechu22 about 2 years ago
- Related to Emulator Issues #9410: Audio Crackling in Homebrew Demo, not present on 4.0.2 added