Skip to content

Add automatic retry mechanism for hotkey registration#8329

Open
tomstetson wants to merge 1 commit intoShareX:developfrom
tomstetson:feature/hotkey-retry-mechanism
Open

Add automatic retry mechanism for hotkey registration#8329
tomstetson wants to merge 1 commit intoShareX:developfrom
tomstetson:feature/hotkey-retry-mechanism

Conversation

@tomstetson
Copy link
Copy Markdown

@tomstetson tomstetson commented Jan 18, 2026

Summary

  • Add automatic retry mechanism for hotkey registration to handle race conditions at startup
  • Fixes the common issue where OneDrive (or other apps) temporarily claim PrintScreen hotkeys before ShareX can register them
  • New configurable settings: HotkeyRetryEnabled, HotkeyRetryCount, HotkeyRetryDelayMs
  • Backward compatible - existing UpdateHotkeys() method preserved

Problem

When ShareX starts, it immediately attempts to register global hotkeys using the Win32 RegisterHotKey API. Other applications like OneDrive often claim these same hotkeys (PrintScreen, Alt+PrintScreen) during their own startup sequence, causing:

  1. ShareX calls RegisterAllHotkeys() immediately at startup
  2. OneDrive has already registered the hotkey
  3. RegisterHotKey returns false, hotkey status set to Failed
  4. "Hotkey registration failed" error dialog shown
  5. User must manually restart ShareX or open Hotkey Settings

Note: OneDrive claims these hotkeys even when its screenshot feature is disabled.

Solution

New Method: UpdateHotkeysWithBackgroundRetry()

  • Performs initial registration synchronously (fast startup)
  • If hotkeys fail, starts background retry task (fire-and-forget)
  • Does not block IsReady - CLI invocations from second instances work immediately
  • Shows error dialog only after all retry attempts are exhausted

New Configuration Settings (ApplicationConfig)

Setting Default Range Description
HotkeyRetryEnabled true - Enable/disable automatic retry
HotkeyRetryCount 3 1-10 Number of retry attempts
HotkeyRetryDelayMs 2000 500-30000 Delay between retries (ms)

Security Considerations

Settings are clamped to safe ranges to prevent DoS via malicious config files:

  • Max retry count: 10 (prevents infinite loops)
  • Max delay: 30 seconds (prevents extreme startup delays)
  • Worst case: 10 × 30s = 5 minutes background retry window

Files Changed

File Changes
ShareX/ApplicationConfig.cs Added 3 new settings for retry configuration
ShareX/HotkeyManager.cs Added UpdateHotkeysWithBackgroundRetry(), RetryFailedHotkeysInBackgroundAsync(), and HasFailedHotkeys()
ShareX/Forms/MainForm.cs Updated InitHotkeys() to use non-blocking retry method

Related Issues

Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 9257f5a787

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread ShareX/Forms/MainForm.cs Outdated
Comment on lines +368 to +369
// Use retry mechanism to handle race conditions with other apps (e.g., OneDrive)
await Program.HotkeyManager.UpdateHotkeysWithRetryAsync(Program.HotkeysConfig.Hotkeys, !Program.IgnoreHotkeyWarning);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Avoid blocking InitHotkeys on retry delays

Awaiting UpdateHotkeysWithRetryAsync here means startup readiness is delayed by the full retry window whenever hotkey registration fails (e.g., OneDrive holding PrintScreen). Because IsReady isn’t set until InitHotkeys completes (see UpdateControls), WaitFormLoad(5000) in Program.cs gives up after 5 seconds and drops command-line arguments from a second instance if the retries take longer than that. This makes CLI invocations flaky specifically in the hotkey-conflict scenario the change is trying to improve. Consider running retries without blocking readiness (e.g., fire-and-forget or set IsReady before waiting), or otherwise ensuring WaitFormLoad still succeeds during long retries.

Useful? React with 👍 / 👎.

- Initial registration is synchronous (fast startup)
- Retries run in background to avoid blocking WaitFormLoad
- Fixes race condition with OneDrive claiming hotkeys at startup
- Configurable via HotkeyRetryEnabled, HotkeyRetryCount, HotkeyRetryDelayMs
- Values clamped to safe ranges to prevent DoS via malicious config
@tomstetson tomstetson force-pushed the feature/hotkey-retry-mechanism branch from 9257f5a to 6abad76 Compare January 18, 2026 16:19
@tomstetson
Copy link
Copy Markdown
Author

Addressed Codex Review Feedback

Thanks for the review! I've updated the implementation to address the P2 - Avoid blocking InitHotkeys on retry delays feedback.

Changes Made:

  • Renamed UpdateHotkeysWithRetryAsync()UpdateHotkeysWithBackgroundRetry()
  • Initial registration is now synchronous - returns immediately after first attempt
  • Retries run in background via fire-and-forget (_ = RetryFailedHotkeysInBackgroundAsync())
  • IsReady is set immediately after initial registration, before retries complete

Result:

  • WaitFormLoad(5000) now succeeds immediately since IsReady is set right away
  • CLI invocations from second instances work correctly even during retry window
  • Retries still happen in background and show error dialog only after exhausting all attempts

@github-actions github-actions bot added the Stale label Apr 19, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant