Commit Graph

1642 Commits

Author SHA1 Message Date
Shokunin 91d780bc0a Let a title claim a direct host shortcut; add a debug host-pad layer
psx_mod_allow_direct_shortcut(PSX_MOD_SHORTCUT_*) lets a host shortcut
bound to one controller button act on that button alone. Without it a
one-button binding means Select + button, like the legacy encoding, so a
title can default to a one-button binding safely whether or not its mod is
enabled. While allowed (Rewind: while Rewind is enabled) the runtime claims
the host button: it never reaches P1's guest pad, and a claim made while it
is held lasts until release. Allowances clear at every mod session start.
Multi-button bindings behave as before.

game.toml [controller] direct_shortcut / direct_shortcut_button lets the
title default that shortcut to one button and tells the launcher to capture
it as one button (RECOMP_LAUNCHER_HAS_DIRECT_ASSIST_BIND). No title id is
checked anywhere.

Debug: set_input {"layer":"host", buttons, lx..ry, lt, rt} arms a
virtual P1 gamepad that feeds stage 1 of the offline input path (so sources,
title transforms and trigger values see it) and shortcut polling. A plain
set_input override still wins. Headless runs with the layer armed resolve
P1 through the same path and poll Rewind and the fast-forward latch; the
Rewind pause loop keeps the debug endpoint live and runs without a window.

Binding semantics and the claim latch are pure (psx_hotkey_pad.h) and
covered by psx_hotkey_pad_test.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 20:25:17 -07:00
Shokunin 82bc90dff2 Give a title pad transform the host pad of a digital-presented player
A digital presentation folds the sticks onto the D-pad and centres them,
so a transform on a digital player (the default for many titles) never
saw the stick. The transform decides what the guest sees, so for a
digital stage-1 pad with no controller source its frame is now the host
pad: real sticks and buttons without the stick->D-pad fold, type still
DIGITAL (new PadExtHooks.host_pad, capture_pad_slot_view). The output is
pre-filled with the stock pad and a decline delivers it, so pass-through
stays the stock folded digital bytes (mod_pad_transform_run takes the
stock pad). Analog pads, sources and guarded frames are unchanged.

Tests: pad_external_input_test (digital player: frame has the real lx and
unfolded buttons, decline and pass-through deliver the stock digital
bytes, no host-pad query for analog / guarded / source ports),
mod_pad_transform_test (decline returns the stock pad, output pre-filled
from it).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 20:24:54 -07:00
Shokunin a4d1f31487 Add a title pad transform stage to external offline input
psx_mod_set_pad_transform(player, &PSXModPadTransform) registers stage 2b
of pad_external_input: after the physical pad and any controller source,
before the mouse policy. The transform sees the resolved pad plus the
port's host extras (gamepad present, LT/RT 0..255 from SDL, unthresholded)
and may rewrite buttons, sticks and the presented controller type, e.g. a
NeGcon whose I/II come from the triggers. Output is pre-filled as a
pass-through, validated (struct size, ranges, type within allowed_types)
and replaced by neutral when invalid; detaching or a mod/session reset
owes one neutral release frame. initial_type sets the boot/hotplug type.

The resolver stays pure: host extras arrive through a new capture hook and
the transform through another, both covered in pad_external_input_test.
Under the input guard the transform runs on zero triggers and its output
is neutralized. A NeGcon result resets the mouse policy rather than letting
it overwrite the I/II bytes. Offline only: netplay, resim, selfcheck replay
and plain debug overrides never reach it.

With no transform registered every pad is bit-identical to before.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 19:36:34 -07:00
Shokunin 514cf5deda Carry the NeGcon type through PsxNetPad and one shared SIO apply
PsxNetPad type 3 is NeGcon, packed lx = twist, rx = I, ry = II, ly = L
(the rollback row's stick view carries twist and L). Every decoder accepts
up to PSX_NETPAD_TYPE_MAX instead of clamping at JogCon, and normalization
keeps NeGcon pressures exact (only twist gets the centre deadzone).

psx_pad_apply_to_sio() is now the one PsxNetPad -> SIO path for offline
sampling, netplay delay/rollback apply and selfcheck replay, so a type
added once reaches the guest the same way everywhere. Selfcheck replay now
matches offline sampling on multitap seats with the analog-on-tap hack.
psx_netplay_normalize_pad moves to a pure TU so tests link the real one
instead of a mirror. Pins recomp-net to the branch that keeps type 3.

Other titles: pads never carry type 3, so SIO bytes are unchanged.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 19:28:13 -07:00
Shokunin ca82734bb8 sio: add the NeGcon (0x23) controller type
SIO_PAD_NEGCON = 3 presents a Namco NeGcon (NPC-101): poll ID 0x23 with
buttons, twist (left X), then analog I, II and L (Mednafen negcon.cpp).
sio_set_pad_negcon() supplies I/II/L per frame like the sticks. The device
has no config mode: any command but 0x42 gets the ID byte with no ACK, and
game bytes in a poll drive no motors. Multitap seats stay digital unless the
analog-on-tap hack is armed; the bulk status block carries the NeGcon frame.

Entering or leaving NeGcon is a device swap, not the DualShock analog
button: a deferred request applies even while the game holds the 0x44 mode
lock, and the swap clears the lock, config latch and motor map. Requests
raised mid-config still wait for config exit.

0x44 now selects the analog mode of the device in the port: a JogCon the
game set to digital returns as a JogCon instead of becoming a DualShock.
The mode lock and that device are guest state, so they join the snapshot
as an appended section (older snapshots still load, unlocked).
pad_status reports negcon and mode_locked per slot.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 19:25:38 -07:00
Shokunin 2388a5ff7f Merge remote-tracking branch 'origin/master' into feat/jogcon-controller
# Conflicts:
#	runtime/src/main.cpp
2026-10-05 14:51:54 -07:00
Matthew Stanley 6f9bdd94f2 Resolve controller source and mouse policy in one ordered external-input layer
Mouse policy now folds onto the resolved pad (source included) instead of a discarded capture; no-policy path does no mouse polling.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-05 13:49:35 -07:00
Matthew Stanley c00a09e556 Collapse identical SDL2/SDL3 arms in local mouse focus()
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
(cherry picked from commit 12d98c2202)
2026-10-05 13:49:35 -07:00
Matthew Stanley f7ca7237cd Reconcile a LEFT release missed while unfocused on focus regain
Non-Windows only reconciled while focused AND captured; focus loss drops capture, so a release outside the window left activation_down_ stuck. Decision moved to LocalMousePolicy::sync_left (tested).

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
(cherry picked from commit f012cf1693)
2026-10-05 13:49:35 -07:00
Beman 93371b1782 Preserve ordered mouse re-press after delayed release
(cherry picked from commit 50ec9191c2)
2026-10-05 13:49:35 -07:00
Beman b5566c7b25 Support optional held mouse input policies for local P1
(cherry picked from commit 00ee1f40b6)
2026-10-05 13:49:35 -07:00
Matthew Stanley 9f13dd0bbc openxr: suspend presentation interpolation while a session runs; glDeleteProgram optional
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-10-05 13:41:02 -07:00
Matthew Stanley 78da432f1e Merge origin/master into pr497
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-10-05 13:39:19 -07:00
Matthew Stanley ad29fcf29d Merge remote-tracking branch 'origin/master' into landtmp/504 2026-10-05 13:25:30 -07:00
Matthew Stanley 19f009600c Merge remote-tracking branch 'origin/master' into landtmp/505
# Conflicts:
#	runtime/tests/test_gte_register_access.cpp
2026-10-05 13:25:10 -07:00
Matthew Stanley b31c40c2ae Merge remote-tracking branch 'origin/master' into landtmp/460 2026-10-05 13:24:39 -07:00
Matthew Stanley 9c88657abc Merge remote-tracking branch 'origin/master' into landtmp/496
# Conflicts:
#	docs/TCP_COMMANDS.md
#	runtime/runtime.cmake
2026-10-05 13:24:20 -07:00
Matthew Stanley a6674e6629 Merge remote-tracking branch 'origin/master' into landtmp/495
# Conflicts:
#	runtime/CMakeLists.txt
#	runtime/src/main.cpp
2026-10-05 13:24:03 -07:00
Matthew Stanley 82468f30d4 Merge remote-tracking branch 'origin/master' into landtmp/494 2026-10-05 13:23:40 -07:00
Matthew Stanley 96375896de Merge remote-tracking branch 'origin/master' into landtmp/493 2026-10-05 13:23:22 -07:00
Matthew Stanley 0da8c607b4 Merge remote-tracking branch 'origin/master' into landtmp/492
# Conflicts:
#	docs/TCP_COMMANDS.md
2026-10-05 13:23:03 -07:00
Shokunin 1424727444 Add deterministic debug pad selection at boot 2026-10-05 13:14:10 -07:00
Shokunin 8233aa889d Match JogCon configuration command responses 2026-10-05 12:57:42 -07:00
Shokunin 83eb147083 Enable JogCon config handshake on deferred selection 2026-10-05 12:57:42 -07:00
Shokunin b44c72349d Test JogCon steering, hotplug and live input 2026-10-05 12:57:31 -07:00
Shokunin 3df760f524 Add JogCon input selection and hotplug handling 2026-10-05 12:57:31 -07:00
Shokunin 52c6d758a6 Add JogCon SIO controller support 2026-10-05 12:57:10 -07:00
Shokunin 13cea2407f test(pgxp): link the session harness without a GTE backend
pgxp.cpp now calls gte_geometry_correction_lookup_probe for pre-draw
probes; the session harness links pgxp.cpp without gte.cpp, so give it
the same no-op stub it already has for gte_geometry_correction_lookup.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 12:41:59 -07:00
Matthew Stanley c20a32fa2d Merge land/pr493 into land/pr496 2026-10-05 10:12:14 -07:00
Matthew Stanley 67e42e8833 mod controller source: call these offline controller sources, mod-trusted, not 'trusted'
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-10-05 10:12:08 -07:00
Matthew Stanley 3733764362 Merge origin/master into land/pr495 2026-10-05 10:11:51 -07:00
Matthew Stanley 091fb61d13 Merge land/pr490 into land/pr491
# Conflicts:
#	docs/TCP_COMMANDS.md
2026-10-05 10:11:45 -07:00
Matthew Stanley 029629ff89 Merge origin/master into land/pr494 2026-10-05 10:11:43 -07:00
Matthew Stanley e1673a52f2 Merge land/pr492 into land/pr493 2026-10-05 10:11:34 -07:00
Matthew Stanley 8bb46116ec Merge origin/master into land/pr490
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-10-05 10:11:10 -07:00
Matthew Stanley 4a276ef0a2 Merge origin/master into land/pr492 2026-10-05 10:11:09 -07:00
Yves a0ed4f7dec openxr: allowlist the color GL fixture in the test-registration guard
runtime/tests/test_openxr_color_gl.c is compiled and run by
run_openxr_color_gl.py (a real-GL fixture, like test_gl_readback_region.c),
not a ctest binary. Without the allowlist entry the recompiler project fails
its test-registration check, which blocks configuring that tree.
2026-10-05 23:42:04 +08:00
Yves a8d859f38b Match encoded desktop colors in OpenXR gameplay and native copies 2026-10-05 23:15:48 +08:00
Yves 5a4a5ee94c tests: link the OpenXR core and guest clock into the GL fixtures
The shared GL fixture (test_gl_scale_invariance.c) includes
gpu_gl_renderer.c directly. It now reads psx_cycle_count and
g_psx_vblank_cycles and calls the psx_openxr_* core, none of which the GL
filter/scale runners provided, so gl_texture_filter_test failed to link.

Define the same guest-clock stand-ins as test_gl_readback_region.c and
compile psx_openxr.c (its no-op shims without PSX_OPENXR) into the two
runners, as run_gl_readback_region.py already does.
2026-10-05 21:41:42 +08:00
Yves 28c55408d5 tests: define the guest clock the shared GL fixture's renderer reads
The shared GL fixture (test_gl_scale_invariance.c) includes
gpu_gl_renderer.c directly. The stereo-pair freshness check added for
render passes reads psx_cycle_count and g_psx_vblank_cycles, which the
fixture never provided, so gl_texture_filter_test failed to link on
Windows (and the non-Windows scale test would too).

Define the same test stand-ins as test_gl_readback_region.c.
2026-10-05 21:20:08 +08:00
Shokunin 5807fe8ec3 fix(pgxp): keep probe out of geometry counters 2026-10-05 03:40:41 -07:00
Shokunin ef768ada9c fix: fall back for unrecognized Windows build tags 2026-10-05 03:23:18 -07:00
Matthew Stanley 75294473a2 fix(renderer): preserve perspective world UVs through camera rounding 2026-10-04 23:18:39 -07:00
Matthew Stanley 3358f81e25 Let titles audit withheld plugin packages; SPU upload wraps like hardware
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 21:53:37 -07:00
Matthew Stanley 911426552a Add shared seamless-loading kit: resident disc packs and guest services
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 20:55:30 -07:00
Matthew Stanley e9da6ab8b1 Reconcile PGXP field rebase with exact agreement; fix merged test links
Rebase a shadow onto GP0's 11-bit field only when flag bits sit above it;
a plain overflowed number keeps master's exact-agreement check.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 19:37:19 -07:00
Matthew Stanley 559f5011c9 Drop duplicated merge test helpers; link gpu_timeline into DMA fixture
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 19:29:17 -07:00
Matthew Stanley 6f0b6378dd Merge effective-disc host reads into the master integration
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 19:27:34 -07:00
Matthew Stanley fe42da2744 Merge release/native-rendering-20261003 into master
Keeps both lines: master's PGXP session, draw-distance clamps, masked rejects
and saturated-winding NCLIP; the release's render-pass kit additions, verified
media/disc extents, timeline/present rings, cull-scale sites. Overlay ABI v30.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 19:27:02 -07:00
Matthew Stanley 4e8652fe2d Make host disc reads see the effective modded disc
Apply committed sector mods during plugin activation, resolve paths through
patched directory records, and bound file size by CD capacity.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 18:53:09 -07:00