Can a critical section object be stored in a std::vector?

Viewed 217

According to the documentation, a critical secion object cannot be copied or moved.

Does that imply it cannot be safely stored in a std::vector style collection as an instance?

1 Answers

Correct; the CRITICAL_SECTION object should not be copied/moved as it may stop working (E.g. perhaps it contains pointers to itself).

One approach would be to store a vector of smart pointers, e.g. (C++17 code):

#include <windows.h>
#include <memory>
#include <vector>

using CS_ptr = std::unique_ptr<CRITICAL_SECTION, decltype(&DeleteCriticalSection)>;

CS_ptr make_CriticalSection(void)
{
    CS_ptr p(new CRITICAL_SECTION, DeleteCriticalSection);
    InitializeCriticalSection(p.get());
    return p;
}

int main()
{
    std::vector<CS_ptr> vec;
    vec.push_back( make_CriticalSection() );    
}

Consider using std::recursive_mutex which is a drop-in replacement for CRITICAL SECTION (and probably just wraps it in a Windows implementation), and performs the correct initialization and release in its destructor.

Standard mutexes are also non-copyable so for this case you'd use std::unique_ptr<std::recursive_mutex> if you wanted a vector of them.

As discussed here also consider whether you actually want std::mutex instead of a recursive mutex.

NOTE: Windows Mutex is an inter-process object; std::mutex and friends correspond to a CRITICAL_SECTION.


I would also suggest reconsidering the need for a vector of mutexes; there may be a better solution to whatever you're trying to do.

Related