Skip to content

fix: reduce paste_suppress_until window from 2s to 200ms (closes #237)#238

Merged
psmux merged 1 commit into
masterfrom
fix/typing-freeze-paste-suppress-window
Apr 18, 2026
Merged

fix: reduce paste_suppress_until window from 2s to 200ms (closes #237)#238
psmux merged 1 commit into
masterfrom
fix/typing-freeze-paste-suppress-window

Conversation

@tarikguney

@tarikguney tarikguney commented Apr 18, 2026

Copy link
Copy Markdown
Collaborator

Summary

Why

paste_suppress_until blocks KeyCode::Char(c) events while the window is in the future (pre-existing check at src/client.rs:2079–2107). Commit 3bf380d (#197) added five new call sites that set this window to now + 2s, including STAGE2_TIMEOUT — which fires when paste_pend accumulates typed chars without a Ctrl+V within 300ms. That is the exact pattern of normal fast typing, so fast typing trips the stage2 heuristic, sets a 2-second suppression window, and silently drops every subsequent keystroke for 2 seconds. See #237 for the full bisect and root-cause analysis.

The 2-second window is far longer than the race it guards. Original motivation (#197): ConPTY may inject clipboard characters asynchronously after a Ctrl+V Release event arrives, so a subsequent Event::Paste / stage2 burst could cause a double-send. This async inject completes in well under 50ms on tested Windows 11 systems. 200ms is a comfortable margin while staying below human-perceptible typing latency.

Test plan

Tested on Windows 11 / pwsh 7 / Windows Terminal 1.23 / PSReadLine 2.4.5:

  • Fast typing no longer stalls. Verified by sustained typing in a psmux session — previously reproduced the 2s freeze every few seconds; with this change, no stalls observed.
  • Single-line Ctrl+V paste — hello world arrives exactly once.
  • Multi-line Ctrl+V paste — 3-line snippet arrives intact, no duplication.
  • Rapid sequential Ctrl+V (×3 in quick succession) — all three instances delivered, none duplicated.
  • Existing psmux test suite passes (no changes to compile or test harness).

Risk / rollout

  • Worst-case regression if 200ms proves insufficient on slower hardware: paste duplication under a specific timing window. Easy to tune upward if reports surface.
  • Alternative minimal fix (if reviewers prefer): remove the KeyCode::Char suppression check entirely and rely on paste_pend timing plus bracketed-paste Event::Paste for dedup. Happy to switch to that approach.

Closes #237

The 2s window silently drops every typed character on Windows for 2
seconds whenever any of five paste-detection code paths fires. Fast
typing fills paste_pend faster than the 300ms stage2 quiet period, so
normal typing bursts get misclassified as paste and the next 2s of
input is dropped. User observation: type → nothing appears → wait a
couple of seconds → typing resumes.

ConPTY's async clipboard-inject race (the original reason for the
suppression) resolves in under 50ms. A 200ms window keeps a 4x margin
over the race it guards while being well below human-perceptible
typing latency.

No behavior change for paste: tested single-line, multi-line, and
rapid sequential Ctrl+V — all deliver once, no duplication.

Closes #237
@psmux psmux merged commit d300b9e into master Apr 18, 2026
8 checks passed
@psmux

psmux commented Apr 18, 2026

Copy link
Copy Markdown
Owner

Thank you @tarikguney for this excellent fix and your thorough analysis in #237. Your bisect to 3bf380d was spot on, and the root cause analysis was crystal clear.

We ran independent E2E validation to prove both the bug and the fix:

Bug Confirmed

Two test suites proved the 2s suppression window was silently dropping legitimate keystrokes:

  1. Batch keystroke injection test: Injected 3+ chars in under 20ms (triggering stage2), then typed more chars during the resulting 2s window. Result: 9 chars silently dropped. Pane showed echo AAADDD instead of echo AAABBBCCCDDD.

  2. Real Ctrl+V paste test: Typed BEFORE, pasted PASTED, then typed AFTER. Result: All 5 chars of AFTER were suppressed. Debug log showed exact timestamps (0.6s after paste, well within the 2s window).

Fix Validated

After applying your change, we verified:

  • Single Ctrl+V: delivered exactly once (no duplication)
  • Multi-line paste: all 3 lines delivered
  • Rapid sequential Ctrl+V: no extra duplication
  • Typing immediately after paste: works (not frozen)
  • Windows path paste (ctrl+v freezes the terminal over SSH #197 trigger): clean output, no trailing tilde
  • TCP send-paste (server code path): delivered once

The 200ms window still provides a 4x safety margin over ConPTY's async inject race (resolves in under 50ms) while eliminating the human-perceptible typing freeze.

Test files for reproduction:

  • tests/test_issue237_final_proof.ps1 (stage2 heuristic freeze)
  • tests/test_issue197_paste_validation.ps1 (comprehensive paste scenarios)

Thanks for the quality contribution. Merged with Co-authored-by credit.

psmux added a commit that referenced this pull request Apr 18, 2026
- typing_bench.cs: cursor-position-based render latency monitor (500Hz)
- burst_bench2.cs: full screen buffer char-count monitor
- injector_batch.cs: batch keystroke injector
- timed_injector.cs: timestamped keystroke injector
- typing_benchmark.cs, burst_benchmark.cs: earlier benchmark tools
- cursor_bench.cs: cursor tracking prototype
- test_realistic_typing.ps1: multi-speed typing benchmark (8/12/20ms)
- test_burst_typing_benchmark.ps1: burst speed comparison
- test_long_paragraph_benchmark.ps1: long text render test
- test_typing_render_latency.ps1: capture-pane render latency
- test_typing_benchmark.ps1: basic typing speed test
- test_sustained_fast_typing.ps1: sustained typing stress test
- test_issue237_final_proof.ps1: issue #237 freeze reproduction
- test_issue237_typing_freeze.ps1: issue #237 debug validation
- test_issue237_typing_freeze_perf.ps1: issue #237 perf variant
- test_issue197_paste_validation.ps1: issue #197 paste validation

These tests proved:
- Issue #237 typing freeze (2s suppress window, fixed in PR #238)
- Issue #197 paste behavior validated (6 test scenarios)
- 15ms P50 overhead at fast typing speeds vs direct PowerShell
- Root cause: 20ms paste_pend buffer delays every keystroke
psmux added a commit that referenced this pull request Apr 18, 2026
Modified typing test suites to include proper test result markers:
- test_realistic_typing.ps1: Validates zero-latency optimization
- test_burst_typing_benchmark.ps1: Validates PR #238 fix
- test_typing_render_latency.ps1: Detects typing freezes
- test_typing_benchmark.ps1: Compares vs direct PowerShell latency
- test_long_paragraph_benchmark.ps1: Validates smooth rendering
- test_sustained_fast_typing.ps1: Tests multiple speed tiers

All tests now output [PASS]/[FAIL] markers compatible with the
run_all_tests.ps1 test runner, allowing typing tests to be included
in automated full test suite runs with proper result aggregation.
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

Successfully merging this pull request may close these issues.

Regression: typing freezes for ~2 seconds intermittently (Windows) — bisected to 3bf380d

2 participants