From 9b3a44b339f5962645558732fcc2ae6112d4b9fb Mon Sep 17 00:00:00 2001 From: Andrew <159703254+andrewsoonqn@users.noreply.github.com> Date: Mon, 29 Jun 2026 15:24:21 +0800 Subject: [PATCH] Parse user print info on the UI thread to prevent heap corruption (#119) get_user_print_info()'s HTTP fetch can run on a worker thread (e.g. BindJob), but parse_user_print_info() mutates userMachineList (insert/erase/delete MachineObject). on_machine_alive (SSDP) mutates the same maps on the UI thread without locking, so parsing off-thread races the map and frees MachineObjects out from under it -> heap corruption. Keep all device-list mutation on the UI thread: parse inline when already on the main thread, otherwise marshal via CallAfter so it stays serialized with on_machine_alive. --- src/slic3r/GUI/DeviceCore/DevManager.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/slic3r/GUI/DeviceCore/DevManager.cpp b/src/slic3r/GUI/DeviceCore/DevManager.cpp index 2d54b5c85f..aa4d360b97 100644 --- a/src/slic3r/GUI/DeviceCore/DevManager.cpp +++ b/src/slic3r/GUI/DeviceCore/DevManager.cpp @@ -851,7 +851,9 @@ namespace Slic3r int result = m_agent->get_user_print_info(&http_code, &body, provider); if (result == 0) { - parse_user_print_info(body); + // parse_user_print_info and on_machine_alive (SSDP for discovery) both mutate the same userMachineList map. + // on_machine_alive mutates the map on the UI thread, do the same for parse_user_print_info. + Slic3r::GUI::wxGetApp().CallAfter([this, body]() { parse_user_print_info(body); }); } }