From 057e9bf4da72df5f00bb1a1ae6de3f9154de234b Mon Sep 17 00:00:00 2001 From: mstembera <5421953+mstembera@users.noreply.github.com> Date: Thu, 16 Jul 2026 08:17:21 +0200 Subject: [PATCH] Fix an MSVC debug break MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit With the latest master I started getting: "A breakpoint instruction (__debugbreak() statement or a similar call) was executed in Stockfish.exe." when debugging in MSVC. I don't really understand the issue but Fable fixed it and I verified it works. Here is its summary: Bug: Calling _get_wpgmptr() in CommandLine::get_binary_directory() triggered a debug CRT assertion failure (__debugbreak()) on Windows. The CRT only initializes the wide program name _wpgmptr when the application uses a wide entry point (wmain). Since Stockfish uses the narrow main(int, char**) entry point, _wpgmptr remains nullptr, and the debug CRT's parameter validation asserts when _get_wpgmptr is called. Fix: Replaced _get_wpgmptr() with GetModuleFileNameW(), which queries the executable path directly from the OS and does not depend on the CRT entry point type. The implementation uses a grow-and-retry loop, so paths longer than MAX_PATH are handled correctly. If the API fails, the code falls back to the original argv0-based behavior. The #ifdef _MSC_VER guard was also removed, since the fix no longer relies on the MSVC CRT — non-MSVC Windows builds (e.g., MinGW) now benefit from the accurate path as well. closes https://github.com/official-stockfish/Stockfish/pull/6972 No functional change --- src/misc.cpp | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/misc.cpp b/src/misc.cpp index dc6dee47f..27762ad4b 100644 --- a/src/misc.cpp +++ b/src/misc.cpp @@ -577,12 +577,15 @@ bool is_whitespace(std::string_view s) { fs::path CommandLine::get_binary_directory(fs::path argv0) { #ifdef _WIN32 - #ifdef _MSC_VER - // Prefer the executable path reported by the CRT when available. - wchar_t* pgmptr = nullptr; - if (!_get_wpgmptr(&pgmptr) && pgmptr != nullptr && *pgmptr) - argv0 = fs::path(pgmptr); - #endif + // Prefer the executable path reported by Windows. Unlike _get_wpgmptr, + // this does not depend on whether the CRT used a narrow or wide entry + // point. Windows paths cannot exceed 32767 characters, so a fixed + // buffer is always sufficient. Falls back to argv0 if the API fails. + constexpr DWORD MaxPath = 32768; + wchar_t path[MaxPath]; + + if (const DWORD length = GetModuleFileNameW(nullptr, path, MaxPath)) + argv0 = fs::path(path, path + length); #endif auto binaryDirectory = argv0.parent_path();