Stop REST fire2/fire3 leaking onto the other joystick port - #880
Merged
chrisgleissner merged 2 commits intoSep 9, 2026
Merged
chrisgleissner merged 2 commits into
chrisgleissner merged 2 commits into
Conversation
apply() mirrored a pressed POTX/POTY into port 1's paddle registers whenever port 2's fire2/fire3 was pressed, and OR'd port 2's extra-button state into port 1's mouse-enable. Pressing fire2/fire3 on one REST joystick port then showed as pressed on the other port's Anykey-style POT read too. Fixes GideonZ#879. Extends tests/e2e/api/input_test.py's joystick Anykey checks with the cross-port case in both directions, and fixes read_joystick_pots to pause the C64 before poking CIA1, matching its sibling helpers: left running, the KERNAL's keyboard-scan IRQ overwrites the paddle-group select within ~20ms of our write, which made the port argument race against it. Verified red/green on real u64 hardware (192.168.1.13): 17/17 joystick checks plus contract and keyboard REST suites pass with the fix, and the same joystick checks correctly fail on the reverted source.
…ystick input Also hardens the GideonZ#879 regression tests: dedup, pot-hardware checks, pause/resume safety, and a shared JOYSTICK_BUTTON_COUNT constant.
Collaborator
Author
|
Confirmed by user to work. Merged. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fixes #879.
JoystickOutput::apply()mirrors an asserted-low POTX/POTY value into port 1's paddle registers whenever port 2'sfire2/fire3is pressed, and OR's port 2's extra-button state into port 1's mouse-enable line. Holdingfire2orfire3on one REST joystick port also reads as pressed on the other port's Anykey-style POT read, matching #879. The fix removes the mirror and the OR term; each port's paddle registers now reflect only that port's ownfire2/fire3state.A second defect:
apply_joystick_event()releases an input by updating persistent state only. Atapon the same input that's still mid-hold keeps its overlay bit pressed, which outranks the new persistent state inJoystickOutput::outputSnapshot()'spersistent & overlaycombination, so the release has no visible effect for up to one 20ms timer tick.JoystickOutput::cancelRestPort1Overlay/cancelRestPort2Overlay, called from the release branch, clear the released bit's overlay and hold countdown immediately.Changes
joystick_output.cc/.h: removes the cross-port mirror and mouse-enable OR term; addscancelRestPortXOverlay+cancel_overlay_bits; replaces a literal7with a namedJOYSTICK_BUTTON_COUNTconstant matchinginput_api.h'sINPUT_API_MAX_JOYSTICK_INPUTS.route_input.cc: calls the new cancel methods on release.input_api_state_test.cpp: two host unit tests for the release/tap fix.input_test.py: Anykey-isolation checks collapsed into one parametrized loop; added a check holdingfire2on port 1 andfire3on port 2 at once (a mirror can't satisfy this by chance the way it can a one-port-at-a-time check); added hardware checks for tap auto-release and for release-in-the-same-batch-as-tap; extended the round-trip andrelease_allchecks to assert POT hardware, not just REST JSON and CIA state;read_joystick_potsnow pauses the C64 like its siblings (unpaused, the KERNAL's keyboard-scan IRQ races the CIA1 write within ~20ms); all three pause-then-read helpers now attemptresume()even ifpause()itself raises; paired-port checks now pause once viaread_joystick_pots_bothinstead of twice.Test plan
Both defects verified red/green on an Ultimate 64 Elite (firmware 3.15, real hardware):
joystick_output.ccreproduces U64 REST Joystick input 2nd/3rd firebutton triggering on both joystick ports #879's exact symptom (expected fire2/fire3=False/False, got True/False); fixed,joystick21/21,contract7/7,keyboard19/19 pass.cancelRestPortXOverlaycalls fails the new same-batch check (response still showsfire2pressed); restored, it passes. Also covered by 2 host unit tests (cd software/api/tests && make input-api-state, 30/30 pass).u64andu64iiboth build cleanly with the full change set.Related, not fixed here
usb_hid.cc's mouse-move handler unconditionally writesC64_PADDLE_1_X/C64_PADDLE_1_Yfrom raw USB mouse position right afterJoystickOutput::apply()writes the same registers from REST state, so an attached USB mouse clobbers a REST-held port-1fire2/fire3. Same register family, a different, uncoordinated writer. No USB mouse was available to verify a fix red/green.