dotnet/wpf · error · Win32Exception

Win32Exception

Error message

Win32Exception

What it means

SafeNativeMethodsCLR.GetKeyboardLayoutList wraps the Win32 GetKeyboardLayoutList API and throws a Win32Exception wrapping Marshal.GetLastWin32Error when the API returns 0 (failure) with a non-zero error code — the list of installed keyboard layouts could not be retrieved.

Solutions

  1. Read the Win32 error code on the exception and address the underlying OS issue (e.g. ERROR_INSUFFICIENT_BUFFER means size handling is broken)
  2. Repair/inspect the keyboard layout Preload registry keys if layouts are corrupted
  3. Avoid calling from non-interactive sessions (services) where keyboard layout APIs may fail
  4. Retry once after failure — transient resource failures can clear

Example fix

// before
int count = SafeNativeMethodsCLR.GetKeyboardLayoutList(0, null); // may throw
// after
int count;
try { count = SafeNativeMethodsCLR.GetKeyboardLayoutList(0, null); }
catch (Win32Exception ex) { log(ex.NativeErrorCode); count = 1; /* fallback to default layout */ }
Defensive patterns

Strategy: try-catch

Try / catch

try { layouts = SafeNativeMethodsCLR.GetKeyboardLayoutList(size, hkls); } catch (Win32Exception ex) { log(ex.NativeErrorCode); layouts = fallbackToDefaultLayout(); }

Prevention

When it happens

Trigger: Calling GetKeyboardLayoutList when the underlying Win32 call fails: invalid size/buffer handling, or an OS-level failure such as insufficient resources or a corrupted keyboard-layout registry state.

Common situations: Input-language enumeration at startup on machines with damaged HKL registry entries (HKLM\...\Keyboard Layout\Preload); running in unusual session or service contexts (session 0) with no input desktop.

Related errors


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

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/Shared/MS/Win32/SafeNativeMethodsCLR.cs:36

        {
            return SafeNativeMethodsPrivate.GetKeyboardLayout(dwLayout);
        }

        public static IntPtr ActivateKeyboardLayout(HandleRef hkl, int uFlags)
        {
            return SafeNativeMethodsPrivate.ActivateKeyboardLayout(hkl, uFlags);
        }

#if BASE_NATIVEMETHODS
        public static int GetKeyboardLayoutList(int size, [Out, MarshalAs(UnmanagedType.LPArray)] IntPtr[] hkls)
        {
            int result = NativeMethodsSetLastError.GetKeyboardLayoutList(size, hkls);
            if (result == 0)
            {
                int win32Err = Marshal.GetLastWin32Error();
                if (win32Err != 0)
                {
                    throw new Win32Exception(win32Err);
                }
            }

            return result;
        }
#endif


        internal static void GetMonitorInfo(HandleRef hmonitor, [In, Out] NativeMethods.MONITORINFOEX info)
        {
            if (!SafeNativeMethodsPrivate.IntGetMonitorInfo(hmonitor, info))
            {
                throw new Win32Exception();
            }
        }


        public static IntPtr MonitorFromPoint(NativeMethods.POINT pt, int flags)

View on GitHub (pinned to 81131a70a4)