From 4023febe13cda0e6f313bd7c220eebeee8e3d402 Mon Sep 17 00:00:00 2001 From: Egor Mikhaylov Date: Tue, 23 Jul 2024 14:06:26 +0300 Subject: [PATCH] Fix iterator invalidation bug. --- .../interprocess/sync/windows/sync_utils.hpp | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/include/boost/interprocess/sync/windows/sync_utils.hpp b/include/boost/interprocess/sync/windows/sync_utils.hpp index bbbff63a..e431df39 100644 --- a/include/boost/interprocess/sync/windows/sync_utils.hpp +++ b/include/boost/interprocess/sync/windows/sync_utils.hpp @@ -122,8 +122,9 @@ class sync_handles //key: id -> mapped: HANDLE. Hash map to allow efficient sync operations typedef boost::container::flat_map id_map_type; - //key: ordered address of the sync type -> iterator from id_map_type. Ordered map to allow closing handles when unmapping - typedef boost::container::flat_map addr_map_type; + //key: ordered address of the sync type -> key from id_map_type. Ordered map to allow closing handles when unmapping + // Can't store iterators into id_map_type because they would get invalidated. + typedef boost::container::flat_map addr_map_type; static const std::size_t LengthOfGlobal = sizeof("Global\\boost.ipc")-1; static const std::size_t StrSize = LengthOfGlobal + (sizeof(sync_id)*2+1); typedef char NameBuf[StrSize]; @@ -192,7 +193,7 @@ class sync_handles void *&hnd_val = it->second; if(!hnd_val){ BOOST_ASSERT(map_.find(mapping_address) == map_.end()); - map_[mapping_address] = it; + map_[mapping_address] = id; hnd_val = open_or_create_mutex(id); if(popen_created) *popen_created = true; ++num_handles_; @@ -213,7 +214,7 @@ class sync_handles void *&hnd_val = it->second; if(!hnd_val){ BOOST_ASSERT(map_.find(mapping_address) == map_.end()); - map_[mapping_address] = it; + map_[mapping_address] = id; hnd_val = open_or_create_semaphore(id, initial_count); if(popen_created) *popen_created = true; ++num_handles_; @@ -250,9 +251,11 @@ class sync_handles ithig(map_.lower_bound(hig_id)), it(itlow); for (; it != ithig; ++it){ - id_map_type::iterator uit = it->second; + sync_id ukey = it->second; + id_map_type::iterator uit = umap_.find(ukey); + BOOST_ASSERT(uit != umap_.end()); void * const hnd = uit->second; - umap_.erase(uit); + umap_.erase(ukey); int ret = winapi::close_handle(hnd); --num_handles_; BOOST_ASSERT(ret != 0); (void)ret; //Sanity check that handle was ok