Reputation: 25
I want to create two threads accessing a vector concurrently, such that one keeps pushing elements at the back of the vector every 10 milliseconds, and another simply monitors the vector to see if its size has changed. Here, I get error "unlock of unowned mutex", can you please tell me why.
class SafeVec
{
public:
SafeVec(){}
~SafeVec(){}
void safePushBack(int val)
{
vecMutex.lock();
vec.push_back(val);
vecMutex.unlock();
}
size_t safeGetSize()
{
vecMutex.lock();
size_t size = vec.size();
vecMutex.unlock();
return size;
}
private:
std::vector<int> vec;
std::mutex vecMutex;
};
class safeStream
{
public:
safeStream(){}
~safeStream(){}
void Test()
{
std::thread t(&safeStream::tMonitorVec, this); // spawned a new thread
for (size_t i = 0; i < 100; i++)
{
myVec.safePushBack(1);
Sleep(10);
}
stopMonitoringMutex.lock();
stopMonitoring = true;
stopMonitoringMutex.unlock();
}
private:
void tMonitorVec()
{
stopMonitoring = false;
size_t tempSize = myVec.safeGetSize();
int count = 0;
stopMonitoringMutex.lock();
while (1)
{
if (stopMonitoring)
{
stopMonitoringMutex.unlock();
break;
}
else
{
stopMonitoringMutex.unlock();
if (tempSize != myVec.safeGetSize())
{
count++;
}
}
}
std::cout << count;
}
SafeVec myVec;
bool stopMonitoring;
std::mutex stopMonitoringMutex;
};
int main()
{
safeStream myStream;
myStream.Test();
return 0;
}
Upvotes: 0
Views: 388
Reputation: 48527
This happens in your loop:
while (1)
{
if (stopMonitoring)
{
stopMonitoringMutex.unlock();
break;
}
else
{
// Whoops! I am here again !
stopMonitoringMutex.unlock();
if (tempSize != myVec.safeGetSize())
{
count++;
}
}
}
One more thing to consider: if you are using std::mutex
only to protect concurrent access to field bool stopMonitoring;
use std::atomic<bool> stopMonitoring;
instead, and forget about mutexes.
Upvotes: 3