boost::interprocess::scoped_lock not unlocking the mutex - c++

I use a boost named_mutex to check if there is already a mutex with the corresponding name, and if it is to halt the program because i want to stop other instances of my app to be ran.
I do this. at the beginning of the program:
try {
boost::interprocess::named_mutex mutex_to_lock(boost::interprocess::open_only, "scilock");
exit(0);
} catch (...) {
boost::interprocess::named_mutex mutex_to_lock(boost::interprocess::create_only, "scilock");
boost::interprocess::scoped_lock locking(mutex_to_lock);
}
*rest of the program...*
It tries to open a mutex first, if it exists, it exits, and if one doesn't exists it throws an exception meaning that we can go ahead and create one. I use a scoped_lock on the mutex so I don't have to manage the unlocking of it (it should unlock even if the app crashes), however it does not unlock it at all. the mutex remains closed after the program ends.
i have tried using named_recursive_mutex, even though I don't think it helps with anything
i have also tried this format:
boost::interprocess::named_mutex mutex_to_lock(boost::interprocess::open_or_create, "scilock");
boost::interprocess::scoped_lock locking(mutex_to_lock, boost::interprocess::try_lock);
if (!lock) // if it didnt manage to lock (meaning that probably it is already locked)
exit(0);
but overall same results.
If it helps with anything, I am using Fedora 36, with boost 1.76
Minimal reproducible example:
#include <chrono>
#include <iostream>
#include <thread>
#include <boost/interprocess/sync/named_mutex.hpp>
#include <boost/interprocess/sync/scoped_lock.hpp>
int main() {
boost::interprocess::named_mutex mutex_to_lock(
boost::interprocess::open_or_create, "sci");
boost::interprocess::scoped_lock locking(mutex_to_lock,
boost::interprocess::try_to_lock);
if (!locking) {
printf("exiting..");
exit(0);
}
std::this_thread::sleep_for(std::chrono::seconds(5));
return 0;
}
The mutex is not being unlocked on app termination, which is not what i want. I want it closed even if the program is being terminated

Related

Why does the first code NOT cause a dead-lock

#include <iostream>
#include <thread>
#include <chrono>
#include <mutex>
#include <thread>
std::mutex mtx;
void func2() {
mtx.lock();
std::cout << "here is 2" << std::endl;
mtx.unlock();
}
void func1() {
mtx.lock();
std::cout << "here is 1" << std::endl;
func2();
mtx.unlock();
}
int main() {
func1();
}
but if I modify the main func as follows, it cause dead lock
int main() {
std::thread t1(func1);
t1.join();
}
I complied both two by "g++ test.cpp -std=c++11 -lpthread"
Calling lock in the same thread twice (without unlocking the mutex) is undefined. From cppreference:
If lock is called by a thread that already owns the mutex, the behavior is undefined: for example, the program may deadlock.
It may deadlock. Or it may not. The behavior is undefined.
Note that std::recursive_mutex can be locked multiple times (though only up to some unspecified limit). However, code that needs a recursive mutex is more complicated. In your example it would be easier to remove the locking from func1, because it is only called when the mutex is already locked. In general it isn't that simple.

Access violation on WakeAllConditionVariable in DLL shutdown

I have a situation where I have a worker thread in a DLL (node native module) that uses a std::condition_variable for synchronization. When the executable exits it simply kills my worker threads, and since it's a node native module I have no access to the DLLMain, so I don't know about the impending shutdown.
When I try to notify my (killed and therefore non-existing) thread to shut down with notify_all(), the call simply hangs (on Window 7) or crashes (Windows 10).
After some research I found that the RTL is using a CONDITION_VARIABLE internally. I can reproduce the crash with this little code snippet:
#include <Windows.h>
#include <thread>
#include <condition_variable>
#include <chrono>
std::mutex mutex;
std::condition_variable cond;
CONDITION_VARIABLE win_cond = CONDITION_VARIABLE_INIT;
CRITICAL_SECTION cs;
void worker() {
//std::unique_lock<decltype(mutex)> lock(mutex);
//cond.wait(lock);
EnterCriticalSection(&cs);
SleepConditionVariableCS(&win_cond, &cs, INFINITE);
LeaveCriticalSection(&cs);
}
int main()
{
InitializeCriticalSection(&cs);
std::thread thread(worker);
std::this_thread::sleep_for(std::chrono::seconds(1));
// Simulate DLL shutdown with lpReserved != null
::TerminateThread(thread.native_handle(), 0);
//cond.notify_all();
WakeAllConditionVariable(&win_cond); // crash
thread.join();
return 0;
}
My questions are:
Is it me or is it a bug?
What can I do to fix this / work around?
Note that I would like to continue to use the c++ standard libraries as this code has to run on other OSes then Windows.

What happens when child thread crash and main wait for join?

In the following program I created a pthread_t thread1 which crash in function func() . I am interested in what exactly happened for pthread_join command in main() .
I ran below program and in exited normally by printing "complete". I dont know why?
#include <iostream>
#include <string>
#include <vector>
#include <map>
#include <cstring>
#include <climits>
#include <cstdio>
#include<pthread.h>
#include <stdlib.h>
using namespace std;
void* func(void *data)
{
cout<<"Calling func"<<(long)(data)<<endl;
int *a;
cout<<a[2]<<endl;
pthread_exit(0);
}
int main( )
{
pthread_t thread1;
pthread_create(&thread1, 0 , &func, (void*)2);
pthread_join(thread1, NULL);
cout<<"complete"<<endl;
}
The process itself will segfault in your case.
If you were to assign NULL to a you can see that it will crash in all likelyhood. In the current code you invoke a in non deterministic manner. Some random location is referenced by a. Hence behavior is undefined. Sometimes you will see the log statement in main, other times the program will crash. Consider yourself lucky if program crashes on such executions
If the thread does a NULL pointer de-reference, it will take the whole process down. Its a process crash and not a thread crash.
the threads operate mostly independent, meaning that each thread can use a signal-handler to catch a "crash"-signal without having the other threads to be killed aswell. Therefor signal-handlers needs to be added.
source: signal-manpage http://man7.org/linux/man-pages/man7/signal.7.html
A signal may be generated (and thus pending) for a process as a whole
(e.g., when sent using kill(2)) or for a specific thread (e.g.,
certain signals, such as SIGSEGV and SIGFPE, generated as a
consequence of executing a specific machine-language instruction are
thread directed, as are signals targeted at a specific thread using
pthread_kill(3)). A process-directed signal may be delivered to any
one of the threads that does not currently have the signal blocked.
If more than one of the threads has the signal unblocked, then the
kernel chooses an arbitrary thread to which to deliver the signal.

C++ terminate called without an active exception

I am getting a C++ error with threading:
terminate called without an active exception
Aborted
Here is the code:
#include <queue>
#include <thread>
#include <mutex>
#include <condition_variable>
template<typename TYPE>
class blocking_stream
{
public:
blocking_stream(size_t max_buffer_size_)
: max_buffer_size(max_buffer_size_)
{
}
//PUSH data into the buffer
blocking_stream &operator<<(TYPE &other)
{
std::unique_lock<std::mutex> mtx_lock(mtx);
while(buffer.size()>=max_buffer_size)
stop_if_full.wait(mtx_lock);
buffer.push(std::move(other));
mtx_lock.unlock();
stop_if_empty.notify_one();
return *this;
}
//POP data out of the buffer
blocking_stream &operator>>(TYPE &other)
{
std::unique_lock<std::mutex> mtx_lock(mtx);
while(buffer.empty())
stop_if_empty.wait(mtx_lock);
other.swap(buffer.front());
buffer.pop();
mtx_lock.unlock();
stop_if_full.notify_one();
return *this;
}
private:
size_t max_buffer_size;
std::queue<TYPE> buffer;
std::mutex mtx;
std::condition_variable stop_if_empty,
stop_if_full;
bool eof;
};
I modeled my code around this example:
http://www.justsoftwaresolutions.co.uk/threading/implementing-a-thread-safe-queue-using-condition-variables.html
What am I doing wrong and how do I fix the error?
When a thread object goes out of scope and it is in joinable state, the program is terminated. The Standard Committee had two other options for the destructor of a joinable thread. It could quietly join -- but join might never return if the thread is stuck. Or it could detach the thread (a detached thread is not joinable). However, detached threads are very tricky, since they might survive till the end of the program and mess up the release of resources. So if you don't want to terminate your program, make sure you join (or detach) every thread.
How to reproduce that error:
#include <iostream>
#include <stdlib.h>
#include <string>
#include <thread>
using namespace std;
void task1(std::string msg){
cout << "task1 says: " << msg;
}
int main() {
std::thread t1(task1, "hello");
return 0;
}
Compile and run:
el#defiant ~/foo4/39_threading $ g++ -o s s.cpp -pthread -std=c++11
el#defiant ~/foo4/39_threading $ ./s
terminate called without an active exception
Aborted (core dumped)
You get that error because you didn't join or detach your thread.
One way to fix it, join the thread like this:
#include <iostream>
#include <stdlib.h>
#include <string>
#include <thread>
using namespace std;
void task1(std::string msg){
cout << "task1 says: " << msg;
}
int main() {
std::thread t1(task1, "hello");
t1.join();
return 0;
}
Then compile and run:
el#defiant ~/foo4/39_threading $ g++ -o s s.cpp -pthread -std=c++11
el#defiant ~/foo4/39_threading $ ./s
task1 says: hello
The other way to fix it, detach it like this:
#include <iostream>
#include <stdlib.h>
#include <string>
#include <unistd.h>
#include <thread>
using namespace std;
void task1(std::string msg){
cout << "task1 says: " << msg;
}
int main()
{
{
std::thread t1(task1, "hello");
t1.detach();
} //thread handle is destroyed here, as goes out of scope!
usleep(1000000); //wait so that hello can be printed.
}
Compile and run:
el#defiant ~/foo4/39_threading $ g++ -o s s.cpp -pthread -std=c++11
el#defiant ~/foo4/39_threading $ ./s
task1 says: hello
Read up on detaching C++ threads and joining C++ threads.
Eric Leschinski and Bartosz Milewski have given the answer already. Here, I will try to present it in a more beginner friendly manner.
Once a thread has been started within a scope (which itself is running on a thread), one must explicitly ensure one of the following happens before the thread goes out of scope:
The runtime exits the scope, only after that thread finishes executing. This is achieved by joining with that thread. Note the language, it is the outer scope that joins with that thread.
The runtime leaves the thread to run on its own. So, the program will exit the scope, whether this thread finished executing or not. This thread executes and exits by itself. This is achieved by detaching the thread. This could lead to issues, for example, if the thread refers to variables in that outer scope.
Note, by the time the thread is joined with or detached, it may have well finished executing. Still either of the two operations must be performed explicitly.
First you define a thread. And if you never call join() or detach() before calling the thread destructor, the program will abort.
As follows, calling a thread destructor without first calling join (to wait for it to finish) or detach is guarenteed to immediately call std::terminate and end the program.
Either implicitly detaching or joining a joinable() thread in its
destructor could result in difficult to debug correctness (for detach)
or performance (for join) bugs encountered only when an exception is
raised. Thus the programmer must ensure that the destructor is never
executed while the thread is still joinable.
As long as your program die, then without detach or join of the thread, this error will occur. Without detaching and joining the thread, you should give endless loop after creating thread.
int main(){
std::thread t(thread,1);
while(1){}
//t.detach();
return 0;}
It is also interesting that, after sleeping or looping, thread can be detach or join. Also with this way you do not get this error.
Below example also shows that, third thread can not done his job before main die. But this error can not happen also, as long as you detach somewhere in the code.
Third thread sleep for 8 seconds but main will die in 5 seconds.
void thread(int n) {std::this_thread::sleep_for (std::chrono::seconds(n));}
int main() {
std::cout << "Start main\n";
std::thread t(thread,1);
std::thread t2(thread,3);
std::thread t3(thread,8);
sleep(5);
t.detach();
t2.detach();
t3.detach();
return 0;}
yes, the thread must be join(). when the main exit

main doesn't continue after pthread

Im using Ubuntu 10.10, Code::Blocks with GCC 4.2.
I have written a code like that:
#include <iostream>
#include <stdlib.h>
#include <pthread.h>
using namespace std;
void *thread1proc(void* param){
while(true)
cout << "1";
return 0;
}
int main(){
pthread_t thread1;
pthread_create(&thread1,NULL,thread1proc,NULL);
pthread_join(thread1,NULL);
cout << "hello";
}
Main starts, creates the thread. But what is weird (for me) is main doesn't continue running. I expect to see "hello" message on screen and end of the program. Because in Windows, in Delphi it worked for me like that. If "main" is also a thread, why doesn't it continue running? Is it about POSIX threading?
Thank you.
pthread_join will block until thread1 completes (calling pthread_exit or returning), which (as it has an infinite loop) it never will do.
It stops because you call pthread_join and the thread you are joining "to" has an infinite loop.
From that link:
The pthread_join() function suspends
execution of the calling thread until
the target thread terminates, unless
the target thread has already
terminated.