libretro / picodrive

Fast MegaDrive/MegaCD/32X emulator
Other
43 stars 64 forks source link

Run-ahead issues with 32X #156

Open bslenul opened 3 years ago

bslenul commented 3 years ago

While reproducing this issue: https://www.reddit.com/r/RetroArch/comments/ni4vwo/picodrive_32x_and_runahead/ I noticed multiple issue with run-ahead and 32X games:

Video to show the issue in action (with second instance), and step-by-step of what I'm doing and what's going on in it:

https://user-images.githubusercontent.com/33353403/119223329-13fe7b80-baf9-11eb-9b81-8e4441d4d209.mp4

So yeah, super weird šŸ˜… Is it even normal that run-ahead is disabled for 32X?

irixxxx commented 2 years ago

I have done some work on save/load stuff which is also used by run-ahead. Could you try this again please, with a core having at least revision 688c90d?

bslenul commented 2 years ago

Tested briefly, looks like it's still glitchy using 688c90d. It still disables on its own when pressing a button, then there are the weird issues after closing content and starting again, etc.

irixxxx commented 2 years ago

Is this happening too when saving?

bslenul commented 2 years ago

Pressing F2 to save state doesn't disable run-ahead, however Quick Menu > Save State disables it šŸ¤” Loading a state disables it, no matter if you use F4 or the Quick Menu.

irixxxx commented 2 years ago

Hmm. Which platform? Is this only with 32X games? How about MCD, MD, SMS, GG?

bslenul commented 2 years ago

Windows 10 64bit, I could try to reproduce on a Linux VM and Android a bit later.

Run-ahead + states work fine with MD, SMS and GG AFAICT, with MCD it seems broken after the BIOS however, graphical glitches in Night Trap for example:

image

with this kind of stuff in logs:

[libretro INFO] 00855:261: idle: don't know how to restore 4e75
[libretro INFO] 00855:261: idle: don't know how to restore 0026
[libretro INFO] 00855:261: idle: don't know how to restore 08d0

Sonic CD freezes multiple times on its main menu, once in-game it is playable but a bit slow, states work.

irixxxx commented 2 years ago

I think this is due to the fact that save states can't grow over time in retroarch, which is what's happening with 32x, where save states get bigger after 32x is released from reset by the 68000. Try enabling runahead after the image ran up to the sega logo.

bslenul commented 2 years ago

Oooh, yeah if I load Chaotix and enable run-ahead only after loading a level it works fine then!

irixxxx commented 2 years ago

There's no always-working easy test for a rom to check if it's using 32X or not. There's a field in the header which should carry this information, but it's presumably not always correct since it's not checked by the system (e.g. the original Sega SDK sample programs don't have it ;-)). OTOH libretro wants to know about the maximum state save file size for a certain rom in adavance (i.e. on the 1st use of save/load). That would only be securely possible by including the possible use of 32X in the max calculation, increasing the memory needed for each state buffer by roughly 400KB. That doesn't sound much, but may lead to features like run-ahead not working on platform with very low memory.

bslenul commented 2 years ago

OK, thanks for the replies and explanation! Seems tricky to handle indeed... :/

I don't use run-ahead anymore so not affected by this issue anymore but I'm always up for testing stuff, so if you ever come with an idea don't hesitate to ping me (here or on Discord) if you need a tester.

Or I can just close the issue if you don't think it'll be possible to fix on the core side.

irixxxx commented 2 years ago

I'm going to change the max calculation to always include the 32X stuff for MD/MCD. I guess the memory would only be relevant to something like the PS2 (if it offers run-ahead at all). Less ancient systems should probably have enough memory to handle this.

irixxxx commented 2 years ago

I changed something in my repo to cover this, fixing 2 other bugs on the way. It should improve on both MCD and 32X run-ahead. Could you please check this?

bslenul commented 2 years ago

Run-ahead isn't disabled as soon as you press a button anymore, so progress! :D

There are still some weird issues however in 32X and MCD (32X or not) with the image being frozen sometimes until you press or release a button:

image

And here's a quick video showing a few issues I've encountered in Sonic CD:

https://user-images.githubusercontent.com/33353403/147999713-436f83ea-72bc-48d7-8164-809dd4f19870.mp4

You can see the intro glitches, the black screen on loading level, the freeze when hitting a sign and during the boss. For every of these glitches I have to either press a button or release the button I was holding during the freeze.

That was with https://github.com/irixxxx/picodrive/commit/92f7a430ca1c8598514ce5800d28a287d01f699c

irixxxx commented 2 years ago

Ouf, I made an error merging from the dev branch to master. Could you please try this diff, please: y.txt

bslenul commented 2 years ago

OK just tried, all these weird image freezes are still there unfortunately.

irixxxx commented 2 years ago

Is run-ahead configured as 2nd instance for this?

bslenul commented 2 years ago

Yup, 2nd instance ON and a single frame of run-ahead. Without 2nd instance Chaotix doesn't even boot, it stays on a black screen, MCD seems fine however.

irixxxx commented 2 years ago

Could you recheck with the latest from my repo please. I've tried to fix some save/load problems and improve timing accuracy some, for md, mcd and 32x a bit. If possible do so in both one and two instance modes.

bslenul commented 2 years ago

Seems good with 2nd instance now šŸ‘ No more weird image freezes or glitchy FMVs, etc.

Without 2nd instance Chaotix now boots, but sometimes it can't load the level, Knuckles keeps spinning for ever in a completely black background:

https://user-images.githubusercontent.com/33353403/148467173-74fec321-ead2-451b-827f-384044e36aa6.mp4

And sometimes it loads just fine šŸ¤· Same with content restart, sometimes it works fine sometimes it just freezes. I wasn't able to reproduce these 2 issues with 2nd instance.

irixxxx commented 2 years ago

I had a small regression in that code which I fixed. Don't know if it is related though.

bslenul commented 2 years ago

Yeah I was able to trigger the bug after a few retries, so probably unrelated. Wish I knew how to reproduce consistently, seems completely random when it happens :/

irixxxx commented 2 years ago

Can't reproduce it under RA on x86 linux :-(

bslenul commented 2 years ago

It's happening on my Linux Mint VM too, but it's 64bit (idk if it matters):

image

irixxxx commented 2 years ago

What's your run-ahead config for this? What exactly have you done?

bslenul commented 2 years ago

In Settings > Latency:

I don't do anything special in-game, just starting it, pressing Start a few times until it loads the 1st level then it's random, either it'll load properly or Knuckles will spin indefinitely on a black screen.

irixxxx commented 2 years ago

No luck with these settings, in a Ubuntu 20 64bit VM...

bslenul commented 2 years ago

Damn :/ Just tried on a fresh install of RA to make sure it's not a setting messing with this but nope, I was able to reproduce the bug after 5 or 6 tries.

irixxxx commented 2 years ago

Hmm. I'm doing this:

that has succeeded for at least 30 times. Is this a problem of the rom version? what's your md5?

bslenul commented 2 years ago

MD5: 47B1095E68B053125CD2CD5B1AC4EB50 which matches No-Intro database. Only tested with the "(Japan, USA)" version.

I'm building the core from your repo by simply using make -f Makefile.libretro -j4, it shouldn't require anything more, right?

edit: Hm, looks like I can't reproduce the bug with the EU version šŸ¤”

irixxxx commented 2 years ago

Your build is fine. I have 2 different md5sums for my 2 versions, though.

bslenul commented 2 years ago

No idea if this is a useful info or not but I just tried disabling dynarec from the core options and it seems to get rid of the issue, although it's always hard to tell for sure due to the random nature of the glitch, but I wasn't able to reproduce in ~50 tries.

irixxxx commented 2 years ago

The timing isn't identical with interpreter and drc. The interpreter maintains the cycle counter on an instruction base, while the drc is doing this on a block base (a block being instructions from an address jumped to and the next jump). The drc is usually overdrawing its cycle budget for some instructions, while the interpreter stops after the instruction where the cycle budget runs out. This usually isn't a problem, but additionally the exact sh2 cycle counters at save state generation aren't stored, which introduces some inaccuracy on load since that drc overdraw is taken out. I changed this, but now the level is appearing much later than with run-ahead off. I guess this needs some more investigation.

irixxxx commented 2 years ago

I did more improvments on saving/loading states, which might help here. You might want to check it out.

bslenul commented 2 years ago

After some quick tests it seems to be fixed šŸ‘ Just to be sure I'll do more tests later then close the issue if I can't reproduce anymore :)

bslenul commented 2 years ago

Sorry for the delay! So yeah I can't reproduce the Chaotix bug anymore with single instance, however I have another issue in Night Trap (the 32X version): cameras are replaced with a still image from the intro movie.

Here's a video (you can skip to 0:40):

https://user-images.githubusercontent.com/33353403/154258758-11066ede-f903-4828-985c-de7c6f600cb3.mp4

I don't know if the poor performances are normal also, sound is terrible and video stutters but since it's running without second instance maybe it's normal?

irixxxx commented 2 years ago

Is this running OK without run-ahead?

bslenul commented 2 years ago

Yeah, without run-ahead or with run-ahead + second instance it runs perfectly fine, it performs great and the cameras work properly.