dotnet/wpf · warning · Win32Exception

throw new System.ComponentModel.Win32Exception();

Error message

throw new System.ComponentModel.Win32Exception();

What it means

HwndMouseInputProvider.GetIntermediatePoints calls the Win32 GetMouseMovePointsEx API to retrieve buffered mouse points for high-resolution mouse movement. When the API returns -1 it failed, and the code throws a bare Win32Exception carrying the native error code (commonly ERROR_POINT_NOT_FOUND). This breaks the retrieval of interpolated mouse points that make WPF mouse sampling smooth.

Solutions

  1. Treat the failure as non-fatal at the consumer level and degrade gracefully — intermediate points are an optimization; fall back to the last delivered mouse position.
  2. Check the NativeErrorCode: ERROR_POINT_NOT_FOUND simply means the points aged out of the buffer and can be safely ignored.
  3. Keep the UI thread responsive (avoid long work in mouse handlers) so requests happen while points are still in the system buffer.
  4. If you own a modified build, wrap the GetMouseMovePointsEx call in try/catch and continue with n = 0 points.

Example fix

// before
int n = UnsafeNativeMethods.GetMouseMovePointsEx(size, ref mp_in, mp_out, 64, mode);
if (n == -1)
    throw new System.ComponentModel.Win32Exception();
// after
int n = UnsafeNativeMethods.GetMouseMovePointsEx(size, ref mp_in, mp_out, 64, mode);
if (n == -1)
    n = 0; // points not in buffer anymore; skip intermediate points
Defensive patterns

Strategy: try-catch

Try / catch

try
{
    GetIntermediatePoints(...);
}
catch (Win32Exception ex) when (ex.NativeErrorCode == 0) // or catch-all
{
    // intermediate points unavailable; proceed with last known position
}

Prevention

When it happens

Trigger: Mouse processing requests intermediate points while GetMouseMovePointsEx fails — typically when the requested point's timestamp no longer exists in the system mouse buffer, or when the mp_in structure is stale/invalid (e.g. points requested after a long idle or screen lock).

Common situations: Rapid mouse movement combined with a slow UI thread so the buffer churns before the lookup; resuming from sleep/lock where timestamps in the buffer are stale; remote-desktop or virtualized input environments where the history buffer behaves differently.

Related errors


AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14). Data as JSON: /api/errors/0cec6f216773c057. Report an issue: GitHub.

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/PresentationCore/System/Windows/InterOp/HwndMouseInputProvider.cs:234

                    {
                        int nVirtualWidth  = UnsafeNativeMethods.GetSystemMetrics(SM.CXVIRTUALSCREEN);
                        int nVirtualHeight = UnsafeNativeMethods.GetSystemMetrics(SM.CYVIRTUALSCREEN);
                        int nVirtualLeft   = UnsafeNativeMethods.GetSystemMetrics(SM.XVIRTUALSCREEN);
                        int nVirtualTop    = UnsafeNativeMethods.GetSystemMetrics(SM.YVIRTUALSCREEN);
                        uint mode           = NativeMethods.GMMP_USE_DISPLAY_POINTS;

                        NativeMethods.MOUSEMOVEPOINT mp_in  = new NativeMethods.MOUSEMOVEPOINT();
                        NativeMethods.MOUSEMOVEPOINT[] mp_out = new NativeMethods.MOUSEMOVEPOINT[64];

                        mp_in.x = _latestMovePoint.x;
                        mp_in.y = _latestMovePoint.y;
                        mp_in.time = 0;     // don't use a timestamp here, none of the timestamps we have actually work

                        // get all points in the system buffer
                        int n = UnsafeNativeMethods.GetMouseMovePointsEx((uint)(Marshal.SizeOf(mp_in)), ref mp_in, mp_out, 64, mode);
                        if (n == -1)
                        {
                            throw new System.ComponentModel.Win32Exception();
                        }

                        // decide which points to return
                        cpt = 0;
                        bool ignore = true;
                        for (int i = 0; i < n && cpt < points.Length; i++)
                        {
                            // ignore points that happened after the latest MouseMove
                            if (ignore)
                            {
                                if (mp_out[i].time < _latestMovePoint.time ||
                                    (mp_out[i].time == _latestMovePoint.time &&
                                     mp_out[i].x == _latestMovePoint.x &&
                                     mp_out[i].y == _latestMovePoint.y))
                                {
                                    ignore = false;
                                }
                                else

View on GitHub (pinned to 81131a70a4)