{
 "number": 36105,
 "repo": "bitcoin/bitcoin",
 "url": "https://github.com/bitcoin/bitcoin/pull/36105",
 "title": "bitcoin wrapper: Fix Windows exec so wrapper waits for child process",
 "author": "ryanofsky",
 "author_association": "MEMBER",
 "created_at": "2026-08-27T17:34:36Z",
 "updated_at": "2026-09-17T11:54:53Z",
 "age_days": 20,
 "draft": false,
 "labels": [],
 "milestone": null,
 "base": "master",
 "head_sha": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
 "head_ref": "pr/bitwin",
 "head_repo": "ryanofsky/bitcoin",
 "head_history": [
  {
   "t": "2026-09-09T02:17:21Z",
   "sha": "c02747ea3706e0c028b4be61a4dff054d65f3a3e"
  },
  {
   "t": "2026-09-09T14:36:13Z",
   "sha": "359a57d653406365a6158457e77ff926d6f58d0d"
  },
  {
   "t": "2026-09-09T14:54:05Z",
   "sha": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8"
  },
  {
   "t": "2026-09-09T16:15:11Z",
   "sha": "2b8779842a3fcb4afaa533a0490b9618ccc42c36"
  }
 ],
 "additions": 38,
 "deletions": 20,
 "changed_files": 6,
 "commit_count": 4,
 "size_bucket": "S",
 "mergeable_state": "clean",
 "bot": {
  "drahtbot": {
   "present": true,
   "reviews": {
    "concept_ack": [
     {
      "login": "hebasto",
      "url": "https://github.com/bitcoin/bitcoin/pull/36105#pullrequestreview-5046136756"
     },
     {
      "login": "hodlinator",
      "url": "https://github.com/bitcoin/bitcoin/pull/36105#pullrequestreview-5066222814"
     }
    ]
   },
   "conflicts": [
    {
     "number": 36106,
     "title": "bitcoin wrapper: respect CMAKE_INSTALL_BINDIR/LIBEXECDIR",
     "author": "ryanofsky"
    },
    {
     "number": 32387,
     "title": "ipc: add windows support",
     "author": "ryanofsky"
    }
   ]
  }
 },
 "acks_parsed": {
  "hebasto": {
   "kind": "concept_ack",
   "hash": null,
   "t": "2026-08-27T22:17:58Z",
   "stale": false
  },
  "hodlinator": {
   "kind": "concept_ack",
   "hash": "30ae05a21bdb30e63400385cf6d9dfd87dccfc70",
   "t": "2026-08-31T12:16:07Z",
   "stale": false
  }
 },
 "acks_tally": {
  "ack": 0,
  "stale_ack": 0,
  "concept_ack": 2,
  "approach_ack": 0,
  "nack": 0,
  "concept_nack": 0,
  "approach_nack": 0
 },
 "reviews": {
  "approved": 0,
  "changes_requested": 0,
  "distinct_reviewers": [
   "cyb3ralbert",
   "hebasto",
   "hodlinator",
   "maflcko"
  ]
 },
 "signals": {
  "needs_rebase": false,
  "ci_failed": false,
  "mergeable_state": "clean",
  "last_author_activity": "2026-09-09T16:15:11Z",
  "last_reviewer_activity": "2026-09-17T11:54:52Z",
  "last_reviewer": "maflcko",
  "author_silent_days": 8,
  "waiting_on_author_days": 0,
  "days_since_update": 0
 },
 "refs": {
  "mentioned": [
   33229,
   33593,
   35551,
   35704,
   36190
  ],
  "depends_on": [],
  "fixes": [],
  "linked_issues": [],
  "references": [
   {
    "number": 33229,
    "type": "pull",
    "state": "closed",
    "merged": true,
    "merged_at": "2025-09-25",
    "title": "multiprocess: Don't require bitcoin -m argument when IPC options are used"
   },
   {
    "number": 35551,
    "type": "pull",
    "state": "closed",
    "merged": true,
    "merged_at": "2026-07-29",
    "title": "test: add interface_gui.py to test bitcoin-qt startup"
   },
   {
    "number": 33593,
    "type": "pull",
    "state": "closed",
    "merged": true,
    "merged_at": "2026-09-16",
    "title": "guix: Use UCRT runtime for Windows release binaries"
   },
   {
    "number": 35704,
    "type": "pull",
    "state": "closed",
    "merged": true,
    "merged_at": "2026-08-07",
    "title": "windows: remove deprecated codecvt via UTF-8 narrow APIs"
   },
   {
    "number": 36190,
    "type": "pull",
    "state": "open",
    "merged": false,
    "merged_at": null,
    "title": "test: Check bitcoin wrapper child exit status on windows"
   }
  ],
  "conflicts": [
   36106,
   32387
  ]
 },
 "stack": {
  "shares_commits_with": [
   36190
  ],
  "based_on": [],
  "base_for": [
   36190
  ]
 },
 "review_paths": [
  "src/bitcoin.cpp",
  "src/util/exec.cpp",
  "test/functional/test_framework/test_framework.py"
 ],
 "body": "**Problem**: On Windows, `bitcoin.exe` spawns a child process and immediately exits rather than waiting for it to finish. This breaks capturing output and checking exit codes in scripts and tests.\n\n**Solution**: Switch `util::ExecVp` from `_execvp` to `_spawnvp(_P_WAIT)`, which blocks until the child exits and forwards its exit code. Also enable `tool_bitcoin.py` and `interface_gui.py` tests which were skipped due to previous behavior.\n\nThis fix requires small changes to `src/util/exec.cpp` and `src/bitcoin.cpp` and there is also an extra commit fixing `errno` message strings on Windows when `ExecVp` fails. Details in commit messages.",
 "commits": [
  {
   "sha": "6bce70ad0330467abc38e5ee23f3fc3b4379112b",
   "date": "2026-08-26T15:34:02Z",
   "message": "util: Fix ExecVp on Windows to wait for child process\n\nSwitch from _execvp to _spawnvp(_P_NOWAIT) + _cwait so bitcoin.exe\nwaits for the child process to finish and forwards its exit code.\nPreviously _execvp would exit the parent as soon as the child started,\nmaking it impossible for anything waiting on bitcoin.exe (such as a test\nframework) to track whether the child succeeded or failed. _P_NOWAIT is\nused instead of _P_WAIT so that a child exit code of -1 (0xffffffff) is\nnot confused with a spawn failure: _spawnvp(_P_WAIT) returns -1 for both,\nbut _spawnvp(_P_NOWAIT) returns the child handle on success, and _cwait\nfills a separate status that is forwarded via _exit.\n\nCo-Authored-By: Bortlesboat <169967362+Bortlesboat@users.noreply.github.com>\nCo-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>"
  },
  {
   "sha": "68ae4a0f84b12587b9e2b53d3e306460fad4244a",
   "date": "2026-08-26T15:34:02Z",
   "message": "bitcoin: Fix msvcrt EINVAL regression from _execvp to _spawnvp switch\n\nTreat EINVAL from _spawnvp as \"not found\" on msvcrt so the wrapper moves on\nto the next candidate path. msvcrt's _spawnvp returns EINVAL rather than\nENOENT when the file name has a directory component and the file does not\nexist (see code comment), so after the previous commit switched from _execvp\nto _spawnvp, msvcrt builds threw on the first nonexistent candidate,\nlibexec/bitcoind, instead of trying the others. _execvp and ucrt's _spawnvp\nreturn ENOENT, so ucrt builds (MinGW-ucrt and MSVC) are unaffected and the\nchange is guarded with !defined(_UCRT).\n\nMeasured by calling the CRT functions directly on GitHub's windows-2022 and\nwindows-2025 runners, through msvcrt.dll and ucrtbase.dll via ctypes and\nthrough MinGW (msvcrt and ucrt) and MSVC builds:\nhttps://github.com/ryanofsky/bitcoin/actions/runs/34365395636\nhttps://github.com/ryanofsky/bitcoin/actions/runs/34367754505\n\nCo-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>"
  },
  {
   "sha": "ac15f5654aec8ae96fc814cbab331c580f790250",
   "date": "2026-08-26T15:34:02Z",
   "message": "test: Enable tool_bitcoin.py and interface_gui.py tests on Windows\n\nNow that util::ExecVp on Windows uses _spawnvp(_P_NOWAIT) + _cwait\ninstead of _execvp, the bitcoin wrapper process blocks until the child\nexits and Python can capture its stdout/stderr and exit code normally.\nRemove the Windows skips added in #33229 and #35551.\n\nThe interface_gui.py test is still skipped in vcpkg Qt builds. vcpkg builds Qt\nwith -opengl dynamic, making the minimal platform plugin unusable due to\ninternal Qt bugs. This matches existing logic in src/qt/test/CMakeLists.txt\navoiding the minimal platform plugin with test_bitcoin-qt.\n\nCo-Authored-By: Hodlinator <172445034+hodlinator@users.noreply.github.com>"
  },
  {
   "sha": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "date": "2026-08-26T15:34:02Z",
   "message": "bitcoin: Use generic_category for errno from exec/spawn CRT functions\n\nSwitch from system_category to generic_category when throwing from\nExecVp failure, so errno is read as a POSIX value. On Windows,\nsystem_category interprets codes as Win32 errors, so EINVAL=22 would\nproduce \"The device does not recognize the command\" instead of\n\"Invalid argument\".\n\nCo-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>"
  }
 ],
 "timeline": [
  {
   "t": "2026-08-27T22:17:58Z",
   "kind": "review",
   "who": "hebasto",
   "assoc": "MEMBER",
   "state": "COMMENTED",
   "commit": "30ae05a21bdb30e63400385cf6d9dfd87dccfc70",
   "text": "Concept ACK."
  },
  {
   "t": "2026-08-27T22:23:47Z",
   "kind": "review",
   "who": "hebasto",
   "assoc": "MEMBER",
   "state": "COMMENTED",
   "commit": "30ae05a21bdb30e63400385cf6d9dfd87dccfc70",
   "text": "There is a preliminary understanding among the build crowd that https://github.com/bitcoin/bitcoin/pull/33593 might land shortly after branching off \"32.x\", which renders the \"bitcoin: Fix msvcrt regressions from _execvp to _spawnvp switch\" commit unnecessary."
  },
  {
   "t": "2026-08-31T12:06:56Z",
   "kind": "review_comment",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "path": "test/functional/test_framework/test_framework.py",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": null,
   "text": "In 6ca9199eecd9934563351c6b4b11468b75c6d088 - \"test: Enable tool_bitcoin.py and interface_gui.py tests on Windows\":\n\nThe commit message refers to `_wspawnvp()` and `_wexecvp()`, however we use the non-wide versions in code."
  },
  {
   "t": "2026-08-31T12:13:28Z",
   "kind": "review_comment",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "path": "src/bitcoin.cpp",
   "commit": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8",
   "in_reply_to": null,
   "text": "Checked https://learn.microsoft.com/en-us/cpp/c-runtime-library/reference/spawnvp-wspawnvp?view=msvc-170 but this difference in error codes between runtimes is not documented there. Is it admitted elsewhere?"
  },
  {
   "t": "2026-08-31T12:16:07Z",
   "kind": "review",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "state": "COMMENTED",
   "commit": "30ae05a21bdb30e63400385cf6d9dfd87dccfc70",
   "text": "Concept ACK 30ae05a21bdb30e63400385cf6d9dfd87dccfc70"
  },
  {
   "t": "2026-09-08T08:59:08Z",
   "kind": "review_comment",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "path": "src/util/exec.cpp",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": null,
   "text": "https://github.com/bitcoin/bitcoin/blob/33a363ea250839ca31ea043b7500789d2e5d844b/doc/AI_POLICY.md#L23-L26"
  },
  {
   "t": "2026-09-09T01:45:07Z",
   "kind": "review_comment",
   "who": "ryanofsky",
   "assoc": "MEMBER",
   "path": "test/functional/test_framework/test_framework.py",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": 3894266001,
   "text": "re: https://github.com/bitcoin/bitcoin/pull/36105#discussion_r3963876760\n\n[quoted text omitted]\nGood catch. These changes are older than #35704 and the commit message was not updated when it was merged."
  },
  {
   "t": "2026-09-09T01:46:57Z",
   "kind": "review_comment",
   "who": "ryanofsky",
   "assoc": "MEMBER",
   "path": "src/util/exec.cpp",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": 3956142121,
   "text": "re: https://github.com/bitcoin/bitcoin/pull/36105#discussion_r3956142121\n\nThanks. It's important to me to distinguish words and ideas which are my own from those that come from other sources, so I use co-author tags for this. I think the AI policy was written with a different kind of PR in mind than this one. I understand the changes in this PR and take responsibility for them."
  },
  {
   "t": "2026-09-09T02:14:27Z",
   "kind": "review_comment",
   "who": "ryanofsky",
   "assoc": "MEMBER",
   "path": "src/bitcoin.cpp",
   "commit": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8",
   "in_reply_to": 3894313979,
   "text": "re: https://github.com/bitcoin/bitcoin/pull/36105#discussion_r3894313979\n\n[quoted text omitted]\nIt's not documented anywhere and was just seen in CI. I was meaning to follow up and get more information about this though, so I'll try to do that soon."
  },
  {
   "t": "2026-09-09T02:17:21Z",
   "kind": "force_push",
   "who": "ryanofsky",
   "commit": "c02747ea3706e0c028b4be61a4dff054d65f3a3e"
  },
  {
   "t": "2026-09-09T02:18:09Z",
   "kind": "review",
   "who": "ryanofsky",
   "assoc": "MEMBER",
   "state": "COMMENTED",
   "commit": "c02747ea3706e0c028b4be61a4dff054d65f3a3e",
   "text": "Updated 30ae05a21bdb30e63400385cf6d9dfd87dccfc70 -> c02747ea3706e0c028b4be61a4dff054d65f3a3e ([`pr/bitwin.8`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.8) -> [`pr/bitwin.9`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.9), [compare](https://github.com/ryanofsky/bitcoin/compare/pr/bitwin.8..pr/bitwin.9)) with exit code status fix and test from @Bortlesboat from https://github.com/bitcoin/bitcoin/pull/36190"
  },
  {
   "t": "2026-09-09T14:36:13Z",
   "kind": "force_push",
   "who": "ryanofsky",
   "commit": "359a57d653406365a6158457e77ff926d6f58d0d"
  },
  {
   "t": "2026-09-09T14:38:00Z",
   "kind": "comment",
   "who": "ryanofsky",
   "assoc": "MEMBER",
   "text": "Updated c02747ea3706e0c028b4be61a4dff054d65f3a3e -> 359a57d653406365a6158457e77ff926d6f58d0d ([`pr/bitwin.9`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.9) -> [`pr/bitwin.10`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.10), [compare](https://github.com/ryanofsky/bitcoin/compare/pr/bitwin.9..pr/bitwin.10)) just dropping test commit 00fe470459ff36f22ef4a2e7d3e3e8903dac207b as [requested](https://github.com/bitcoin/bitcoin/pull/36190#issuecomment-5596003309)\n\nUpdated 359a57d653406365a6158457e77ff926d6f58d0d -> 5cfe9d873c7b3ca826467e33b6b650f43957d4e8 ([`pr/bitwin.10`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.10) -> [`pr/bitwin.11`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.11), [compare](https://github.com/ryanofsky/bitcoin/compare/pr/bitwin.10..pr/bitwin.11)) to fix lint (unused os/shutil/subprocess imports in tool_bitcoin.py) https://github.com/bitcoin/bitcoin/actions/runs/34364703981/job/102510308140\n\nUpdated 5cfe9d873c7b3ca826467e33b6b650f43957d4e8 -> 2b8779842a3fcb4afaa533a0490b9618ccc42c36 ([`pr/bitwin.11`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.11) -> [`pr/bitwin.12`](https://github.com/ryanofsky/bitcoin/commits/pr/bitwin.12), [compare](https://github.com/ryanofsky/bitcoin/compare/pr/bitwin.11..pr/bitwin.12)) simplifying MSVCRT workaround and documenting it better"
  },
  {
   "t": "2026-09-09T14:54:05Z",
   "kind": "force_push",
   "who": "ryanofsky",
   "commit": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8"
  },
  {
   "t": "2026-09-09T16:13:44Z",
   "kind": "review_comment",
   "who": "ryanofsky",
   "assoc": "MEMBER",
   "path": "src/bitcoin.cpp",
   "commit": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8",
   "in_reply_to": 3894313979,
   "text": "re: https://github.com/bitcoin/bitcoin/pull/36105#discussion_r3964034373\n\n[quoted text omitted]\nFollowed up and this difference does not seem to be documented anywhere, only observed in CI. Did some more testing though and was able to simplify and write a better comment which is in the latest push"
  },
  {
   "t": "2026-09-09T16:15:11Z",
   "kind": "force_push",
   "who": "ryanofsky",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36"
  },
  {
   "t": "2026-09-10T19:25:54Z",
   "kind": "review_comment",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "path": "test/functional/test_framework/test_framework.py",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": 3894266001,
   "text": "thread https://github.com/bitcoin/bitcoin/pull/36105#discussion_r3894266001:\n\nThanks for the generous attribution.\n\nCommit ac15f5654aec8ae96fc814cbab331c580f790250 \"test: Enable tool_bitcoin.py and interface_gui.py tests on Windows\" happens to be the commit I feel is still I don't fully grasp, but it's more what it's referencing than what it's doing.\n\nWhat it's doing in the scope of interface_gui.py - instead of avoiding to run at all on Windows, only skip when the build is a vcpkg build. It references src/qt/test/CMakeLists.txt but that file is not immediately understandable to me.\nFrom looking at https://qt.developpez.com/doc/6.4/qguiapplication/#platformName-prop I think this is how I would make it more understandable:\n```diff\n--- a/src/qt/test/CMakeLists.txt\n+++ b/src/qt/test/CMakeLists.txt\n@@ -40,12 +40,14 @@ add_test(NAME test_bitcoin-qt\n   COMMAND test_bitcoin-qt\n )\n if(WIN32 AND VCPKG_TARGET_TRIPLET)\n   set(plugin_path \"$<SHELL_PATH:$<PATH:GET_PARENT_PATH,$<PATH:GET_PARENT_PATH,$<TARGET_PROPERTY:Qt6::QWindowsIntegrationPlugin,LOCATION_$<CONFIG>>>>>\")\n   set_property(TEST test_bitcoin-qt APPEND PROPERTY\n     ENVIRONMENT_MODIFICATION\n       # On Windows, vcpkg configures Qt with `-opengl dynamic`, which makes\n-      # the \"minimal\" platform plugin unusable due to internal Qt bugs.\n+      # the otherwise appropriate headless \"minimal\" platform plugin unusable\n+      # due to internal Qt bugs. So override to \"windows\" plugin in order to\n+      # make it work when built in that configuration (VCPKG_TARGET_TRIPLET).\n       QT_QPA_PLATFORM=set:windows\n       QT_PLUGIN_PATH=set:${plugin_path}\n   )\n   unset(plugin_path)\n```\n\nMy impression is that src/qt/test/CMakeLists.txt is supposed to make test_bitcoin-qt actually work, even when built with vcpkg.\n\n*So why would you be changing the functional test to skip something which should be working?*\n\nWell, when I build and run  .\\build\\bin\\Release\\test_bitcoin-qt.exe I get:\n```\nqt.qpa.plugin: Could not find the Qt platform plugin \"windows\" in \"\"\nThis application failed to start because no Qt platform plugin could be initialized. Reinstalling the application may fix this problem.\n```\nSetting it to \"minimal\" has the same result.\n\nI tried printing the plugin path through adding this before the variable is unset:\n```\n  message(\"QT_PLUGIN_PATH=${plugin_path} (plugin_path)\")\n```\nand it prints:\n```\nQT_PLUGIN_PATH=$<SHELL_PATH:$<PATH:GET_PARENT_PATH,$<PATH:GET_PARENT_PATH,$<TARGET_PROPERTY:Qt6::QWindowsIntegrationPlugin,LOCATION_$<CONFIG>>>>> (plugin_path)\n```\nManually setting:\n```\nset QT_PLUGIN_PATH=C:\\Users\\hodlinator\\bitcoin\\build\\vcpkg_installed\\x64-windows\\Qt6\\plugins\n```\nmakes .\\build\\bin\\Release\\test_bitcoin-qt.exe run fine, both with minimal and windows plugins!\n\nSo I wonder if the setting of QT_PLUGIN_PATH in CMakeLists.txt is somehow broken? I'm on CMake 4.4.2.\n\nHaving the QT_PLUGIN_PATH set correctly also makes interface_gui.py run fine when modified to not skip!"
  },
  {
   "t": "2026-09-10T19:27:17Z",
   "kind": "review_comment",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "path": "src/bitcoin.cpp",
   "commit": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8",
   "in_reply_to": 3894313979,
   "text": "Impressive testing by @ryan8or. ^^ (https://github.com/ryanofsky/bitcoin/actions/runs/34367754505)"
  },
  {
   "t": "2026-09-10T19:31:37Z",
   "kind": "review_comment",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "path": "src/util/exec.cpp",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": 3956142121,
   "text": "Yeah, didn't mean to put you in the same category as new-entrant sloppers. But I think it may be good to abide by the same rules or else alter/amend them."
  },
  {
   "t": "2026-09-10T20:27:08Z",
   "kind": "review",
   "who": "hodlinator",
   "assoc": "MEMBER",
   "state": "COMMENTED",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "text": "Reviewed 2b8779842a3fcb4afaa533a0490b9618ccc42c36"
  },
  {
   "t": "2026-09-10T20:37:30Z",
   "kind": "review_comment",
   "who": "hebasto",
   "assoc": "MEMBER",
   "path": "test/functional/test_framework/test_framework.py",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": 3894266001,
   "text": "FWIW, in the QML repo, we use the following [code](https://github.com/bitcoin-core/gui-qml/blob/0d469730b0131913098f8520763957f9b8ac0438/src/qml/CMakeLists.txt#L74-L77):\n```cmake\n    file(GENERATE\n      OUTPUT $<TARGET_FILE_DIR:bitcoin-qt>/qt.conf\n      CONTENT \"[Paths]\\nPrefix = $<PATH:GET_PARENT_PATH,$<PATH:GET_PARENT_PATH,$<TARGET_FILE_DIR:Qt6::QWindowsIntegrationPlugin>>>\\n\"\n    )\n```\n\nThis makes all targets runnable form the build tree on Windows."
  },
  {
   "t": "2026-09-13T05:21:01Z",
   "kind": "review_comment",
   "who": "cyb3ralbert",
   "assoc": "CONTRIBUTOR",
   "path": "src/bitcoin.cpp",
   "commit": "5cfe9d873c7b3ca826467e33b6b650f43957d4e8",
   "in_reply_to": 3894313979,
   "text": "One more observation on this, from a `windows-2022` runner with the cross-built binaries from the #36190 branch (which carries this PR's commits). When the target executable is missing, the error the user sees differs between runtimes:\n\n```\nMSVCRT: Error: execvp failed to execute '...\\bitcoind': Invalid argument\nUCRT:   Error: execvp failed to execute '...\\bitcoind': No such file or directory\n```\n\nThe intermediate lookups in `ExecCommand` accept `EINVAL` as \"not found\" and move on, but the last attempt passes `allow_notfound=false`, so the raw `errno` goes into the `std::system_error`. Mapping `EINVAL` to `ENOENT` in that throw as well would make an MSVCRT build report a missing file the same way UCRT does, instead of \"Invalid argument\"."
  },
  {
   "t": "2026-09-16T17:09:49Z",
   "kind": "comment",
   "who": "hebasto",
   "assoc": "MEMBER",
   "text": "[quoted text omitted]\n\n#33593 has been merged now."
  },
  {
   "t": "2026-09-17T11:54:52Z",
   "kind": "review_comment",
   "who": "maflcko",
   "assoc": "MEMBER",
   "path": "src/util/exec.cpp",
   "commit": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
   "in_reply_to": 3956142121,
   "text": "[quoted text omitted]\n\nI think it is fine to do this, like it was done previously. See e.g. `git log --grep=\"uggested by\"`:  7209eb77902a8bf170fd7fbf6ec2388fec77b115 says: \"Fix was suggested by willcl-ark in...\", etc ...\n\nIf you want to credit Claude for a specific noteworthy thing, I'd list that specific thing, and if the full commit was authored by Claude, you can say verbatim that it was authored by Claude, but also fully reviewed by you.\n\nI think that is clearer to everyone and hopefully addresses your needs. Otherwise, the co-author tags are only useful to you, but not really useful to anyone else."
  }
 ],
 "labels_log": [
  {
   "t": "2026-09-09T14:55:35Z",
   "action": "labeled",
   "label": "CI failed",
   "who": "DrahtBot"
  },
  {
   "t": "2026-09-09T17:24:13Z",
   "action": "unlabeled",
   "label": "CI failed",
   "who": "DrahtBot"
  }
 ],
 "state_log": [],
 "text_chars": 12563,
 "text_tokens_estimate": 3140,
 "changed_paths": [
  "src/bitcoin.cpp",
  "src/util/exec.cpp",
  "test/config.ini.in",
  "test/functional/interface_gui.py",
  "test/functional/test_framework/test_framework.py",
  "test/functional/tool_bitcoin.py"
 ],
 "files": [
  {
   "path": "src/bitcoin.cpp",
   "add": 16,
   "del": 1
  },
  {
   "path": "src/util/exec.cpp",
   "add": 11,
   "del": 1
  },
  {
   "path": "test/config.ini.in",
   "add": 1,
   "del": 0
  },
  {
   "path": "test/functional/interface_gui.py",
   "add": 6,
   "del": 7
  },
  {
   "path": "test/functional/test_framework/test_framework.py",
   "add": 4,
   "del": 0
  },
  {
   "path": "test/functional/tool_bitcoin.py",
   "add": 0,
   "del": 11
  }
 ],
 "test_lines": 29,
 "git": {
  "head": "2b8779842a3fcb4afaa533a0490b9618ccc42c36",
  "head_matches_backup": true,
  "base": "a24110cef7fa36138620f1876cd0722944618d07",
  "commits": [
   {
    "sha": "6bce70ad03",
    "subject": "util: Fix ExecVp on Windows to wait for child process",
    "files": 1,
    "add": 11,
    "del": 1
   },
   {
    "sha": "68ae4a0f84",
    "subject": "bitcoin: Fix msvcrt EINVAL regression from _execvp to _spawnvp switch",
    "files": 1,
    "add": 12,
    "del": 0
   },
   {
    "sha": "ac15f5654a",
    "subject": "test: Enable tool_bitcoin.py and interface_gui.py tests on Windows",
    "files": 4,
    "add": 11,
    "del": 18
   },
   {
    "sha": "2b8779842a",
    "subject": "bitcoin: Use generic_category for errno from exec/spawn CRT functions",
    "files": 1,
    "add": 4,
    "del": 1
   }
  ],
  "patch_truncated": false
 },
 "input_hash": "092d31145851278e",
 "extracted_at": "2026-09-17T16:15:31+00:00"
}