Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Serial Port / Null Modem Games not working properly in WinUAE v5.2.0 compared to WinUAE v4.4 #295

Open
dekkit opened this issue Feb 26, 2024 · 17 comments

Comments

@dekkit
Copy link

dekkit commented Feb 26, 2024

Firstly thanks for all your incredible work on this emulator! Secondly, I recently installed InstallWinUAE5200_x64.msi on a Windows 10 machine (i3), and was struggling to get system link / Null Modem games to run properly.

Note: I am running two instances of WinUAE on the same machine.

Games would detect the serial link, progress to the game then randomly lose sync after anywhere from 20 seconds to a few minutes. Note: When i reboot and try the same games using version 4.4 of WinUAE they both sync up pretty much perfectly and seem to keep sync with each other for the duration of any system link games.

2 x Games Tested

  • Stunt Car Racer (adf)
  • Lotus Turbo 2 (adf)

WinUAE Settings
Config: A500
v1.3 ROM, OCS, 512 KB chip + 512KB slow ram
Cycle Accurate

Under Host -> IO Ports
Serial Port = WinUAE inter-process serial port [Master]
Checkboxes are:
Shared = OFF
RTS/CTS = OFF
Direct = ON
UAESerial.Device = OFF

...on the second instance of UAE running on the same machine (all settings the same)
Serial Port = WinUAE inter-process serial port [Slave]

Noting that the cpu utilisation on the windows PC doesn't seem to get above 5-20%

This behavior also sounds similar to the closed issue for v4.10.1 but seems to be occurring in the latest version:
#252

Being able to play null modem Amiga games is an excellent feature of WinUAE and it would be great to preserve this in future versions. I'm happy to help test any future releases.

FYI - If anyone else is looking for steps how to setup a system link / null modem game mode this is what i used:

  • Download WinUAE version 4.4 (x64) (for now)
  • Run 2 x instances of WinUAE
  • Set both instances to be cycle accurate and match the config.
  • Under Host -> Game Ports - select a distinct controller for each instance
  • Under Host -> IO Ports
    Instance 1 Serial Port = WinUAE inter-process serial port [Master]
    Instance 2 Serial Port = WinUAE inter-process serial port [Serial]

Make sure checkboxes for both instances are set to:
Shared = OFF
RTS/CTS = OFF
Direct = ON
UAESerial.Device = OFF

  • Under Host -> Pri. & Extensions
    Make sure checkboxes for both instances are set to:
    When active
    Run at priority = above normal
    Pause emulation = OFF
    Disable sound = OFF

When inactive
Run at priority = above normal
Pause emulation = OFF
Disable sound = OFF
Disable game controllers = OFF

@tonioni
Copy link
Owner

tonioni commented Mar 14, 2024

Do you see any log messages in either winuae log window when things go wrong? (run both winuae instances with -log command line parameter)

EDIT: Ignore above. Nothing interesting happens, game simply starts working strangely. No clues yet..

@tonioni
Copy link
Owner

tonioni commented Mar 16, 2024

Fixed. Serial port emulation was made too accurate (including overrun/overwriting old data that was not fetched quickly enough) but that does not work very well if received data is buffered (comes outside of emulation) which can return multiple bytes back to back. Now any serial mode except loopback does not allow new byte to arrive before previous one is read and serial receive interrupt bit is cleared.

@dekkit
Copy link
Author

dekkit commented Mar 18, 2024

Was about to start grabbing output logs and just realized youve already fixed it!

Excellent work! Will test on the next build, thank you for this!

As a side, is it possible to connect 2x PC each running UAE via serial over network by linking each IP address using the config settings somehow? (I couldn't find how to do this through my searches and reading the help file so it might be an unusual use case)

My next test to achieve something like this was trying this using something like netcat to redirect one to other (granted there maybe latency issues).

@tonioni
Copy link
Owner

tonioni commented Mar 19, 2024

Unfortunately network won't work (Not even LAN worked stable) because action null-modem cable serial linked games expect really small latency, few milliseconds max latency and multiple bytes transferred in single frame. They really hate data that has variable latency. Games designed to work with modem connection should work.

WinUAE had(?) IP link option in serial port box but I don't remember what happened with it. It wasn't very useful because almost all serial linked games lost sync sooner or later.

@dekkit
Copy link
Author

dekkit commented Mar 19, 2024

Makes sense - thanks again!

@rofl0r
Copy link
Contributor

rofl0r commented Mar 19, 2024

few milliseconds max latency and multiple bytes transferred in single frame

these days home-LANs typically have microsecond latency, even wifi typically stays at 0 ms in ping. i wonder if this would no longer be an issue with current equipment (spoiler: i use linux, not the sluggish windows).

@tonioni
Copy link
Owner

tonioni commented Mar 19, 2024

Of course LAN has very low latency but thats not the problem (back in the day I already had gigabit LAN when most had 100M). TCP/IP is the problem (OS does not really matter, don't reply stupid comments.). Maybe raw packets would work nicely in LAN but they have other issues. Also I don't think any of today's networking hardware or software is designed to transfer single bytes where bytes are sent one by one, with about 1-2ms delay between bytes.

Maybe it works in some situations, maybe not. Not my problem. I hate anything network related because debugging becomes x^10 more complex.

@rofl0r
Copy link
Contributor

rofl0r commented Mar 19, 2024

TCP/IP is the problem

for home LAN UDP would make more sense i guess. it's unlikely any packet gets lost there. you just fire and forget, no need to wait for ACK.

I hate anything network related because debugging becomes x^10 more complex.

oh, alright then. would you be open to accept a PR implementing this? (i'm not gonna do it, but someone else might).

@tonioni
Copy link
Owner

tonioni commented Mar 20, 2024

There is enet-network support hidden in serial port emulation. Which (at least when I did it years ago) was meant for something like that. Perhaps it already works after enabling it.

@dekkit
Copy link
Author

dekkit commented Jun 10, 2024

Fixed. Serial port emulation was made too accurate (including overrun/overwriting old data that was not fetched quickly enough) but that does not work very well if received data is buffered (comes outside of emulation) which can return multiple bytes back to back. Now any serial mode except loopback does not allow new byte to arrive before previous one is read and serial receive interrupt bit is cleared.

WinUAE v5.3.0 (WinUAE5300_x64)

Test Results - using single pc to emulate 2 x instances of Winuae (as per first post and settings)
Stunt Car = seems to be working great, played a single race (serial link) and it didn't lose sync at all. Even alt tabbing between each instance to keep both cars moving forward and on the track / crashing off the course.

Lotus Turbo 2 = serial game kicked off ok but would intermittently flicker "Paused" a few times (for barely a fraction of a second) before eventually losing sync and kicking both players back to the opening credits. I suspect this game might be more sensitive to data timing issues, very briefly pausing slave player until the data get back in sync - I recall seeing this this issue once or twice on v4.4 (i.e. rarely)

Example of the 'Pause' flicker (freeze frame)
image

Looking back at the screen shot i do notice the FPS bouncing around 50 (either slightly above or below) - if not that i do wonder if lotus was expecting to be locked in at a specific slower baud rate for data communication (i'm really just guessing tho)

@tonioni
Copy link
Owner

tonioni commented Mar 7, 2025

Does this still happen in 5.3.1 and 6.0 betas? Serial port emulation was again updated in 5.3.1

@dekkit
Copy link
Author

dekkit commented Mar 13, 2025

Will test this again over the weekend and document my findings on each version.

Stay tuned!

@dekkit
Copy link
Author

dekkit commented Mar 14, 2025

@tonioni Outstanding work! You've successfully resolved this when tested in v6.0.0.0 build 13 (for Lotus 2 - doh see next post):

WinUAE 6.0.0 (Public Beta 13, 2025.03.07) 64-bit (10.0.26100 [1]) 64-bit 9.6.BF02 16 10:18 0

Linked: https://download.abime.net/winuae/files/b/winuae64_6000b13.7z45

I've been playing Lotus Turbo 2 for 40mins solidly tonight and I haven't been able to de-sync it all. There were zero(0) instances of the flickering of the 'pause' text. It works brilliantly!

Over the 40mins both emulated amigas remained sync'd up, this included:

  • playing the 1st level over and over alt-tabbing between instances to keep both cars moving forward (via keyboard controls)
  • changing which player starts the link game (e.g. master starts game then slave starts next game)
  • playing 1st level most of the way through as player 1 (master) with slave player 2 car staying near the starting line.
  • playing 1st level most of the way through as player 2 (slave) with master player 1 car staying near the starting line.
  • playing 1st level all the way through as player 1 (master) with slave player 2 car staying near the starting line, and progressing to the twilight level and racing through first few check points (note: it kept sync all through race including loading next level and starting next race)
  • playing 2nd level in 4player mode (2players per emulated amiga) - both emulated amigas kept sync through all trials. You can see all 4 players in the screen cap/

Image

Worth noting that : v5.3.1 did not fix this. In the first attempt, it timed out very quickly with the intermittent 'pause' text before throwing players back to the menu. So whatever changes you are introducing in v6 - it seems to have done the trick! This seems to be even more robust / stable than the link functionality in version 4.4 of WinUAE!

Many thanks for resolving this one for lotus 2! Any idea what caused it in the end?

@dekkit
Copy link
Author

dekkit commented Mar 14, 2025

Doh! Looks like i wrote too soon! While it did a brilliant job with the much more problematic Lotus 2, Stunt Car Racer now fails to run in system link mode HOWEVER does work properly in v5.3.1

Issues with WinUAE 6.0.0 (Public Beta 13, 2025.03.07) 64-bit (10.0.26100 [1]) 64-bit 9.6.BF02 16 10:18 0:

  • while in sync, when you launch the link game (then jump into 2p practice mode) the games race seems to run ahead of the graphic refresh on screen.
  • You can hear the sounds of the cars revving but the graphics doesn't seem update.
  • both amiga instances seem to be communicating, but the game behavior is very different.

It works fine in 1player mode.

So in summary:

  • use v5.3.1 = Stunt Car Racer
  • use v6.0.0 (Public Beta 13) = Lotus 2

@tonioni
Copy link
Owner

tonioni commented Mar 15, 2025

Confirmed. Stunt Car Racer has really poor serial routines that more or less work accidentally...

Transmit is worse: in vblank routine it sends first byte. Serial transmit finished interrupt starts when transmit buffer is empty, interrupt routine sends new byte (if any pending), then almost immediately checks if buffer is free, if it is, send next byte, if not clear transmit finished interrupt! You are supposed to clear it before sending new byte! Interrupt is lost, stopping serial transmit until next frame. (This explains why game runs but really slowly, it takes dozens of frames to transmit all the data that was supposed to take only single frame..).

This bad logic only works if each time new transmit interrupt happens, there is space for two serial bytes (Amiga serial port has 2 buffers, one that is sending the data, other that accepts new byte when sending is in progress), this causes serial interrupt to happen after 1 whole byte has been sent to the wire, which happens long after interrupt has been cleared, allowing game to work.

Ok, so why does it work on real HW (and in older WinUAE versions): old WinUAE versions always responded that buffer is empty so all pending bytes got sent in single interrupt, without ever running game's buggy transmit interrupts. It works on real HW because WinUAE (due to latency when using interprocess communication or even worse when using real serial ports)) tries to make sure data is always sent slightly faster than requested baud rate to make sure there is never internal buffer overflows. This makes timing "variable", triggering the game bug regularly.

Receive is also quite bad: it assumes each serial receive interrupt equals single byte in serial buffer. Programs are supposed to check serial status bits first before assuming data is there.. This did not cause problems.

Not yet sure how to fix this without too many side-effects and without making serial port emulation less accurate.

@dekkit
Copy link
Author

dekkit commented Mar 16, 2025

Thanks for looking at this!

As an interim approach, would it be feasible implementing both an 'accurate' and 'compatibility' mode/switch for direct connection without bloating the code base and to help handle these weird edge cases / per game quirks?

@tonioni
Copy link
Owner

tonioni commented Mar 17, 2025

I don't have fix yet but I'll fix it properly. I don't like program specific hacks.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants