Based on this question: Timeout for thread.join() (ManuelAtWork's answer) I tried to implement a timeout for my std::threads:
std::vector<std::shared_ptr<TestFlow>> testFlowObjects;
std::thread workerThreads[MAX_PARALLEL_NR]; // maximum of 32 threads
std::vector<std::future<void>> helperThreads;
for(int readerCounter=0; readerCounter<GetNumberOfReader(); readerCounter++)
{
testFlowObjects.push_back(std::make_shared<TestFlow>(m_logFiles));
testFlowObjects.back()->SetThreadID(readerCounter);
testFlowObjects.back()->SetTestResults(m_testResultsVector); // vector of int
workerThreads[readerCounter] = std::thread(&TestFlow::DoWork, testFlowObjects.back());
}
// wait for all threads
for(int threadCount=0; threadCount<GetNumberOfReader(); threadCount++)
{
// use helper threads to be able to join with timeout
helperThreads.push_back(std::async(std::launch::async, &std::thread::join, &workerThreads[threadCount]));
helperThreads.back().wait_for(std::chrono::seconds(5)); // 5 sec
}
It works fine if I use a join instead of the std::future helper thread code, but I can't wait infinite!
With std::future approach it seems not all threads are finished and I got: R6010: abort() has been called
Any ideas how to do it correctly?
I think I have to change it like this:
if(helperThreads.back().wait_for(std::chrono::seconds(5)) == std::future_status::timeout) // WHAT SHOULD I DO HERE???
In short and a recommendation
The approach you posted (ManuelAtWork's answer) is a work around, to use the waiting communication semantics of std::future as an approach to wait with a timeout on a std::thread::join. This could also be achieved with communication via condition variables as the accepted answer mentioned.
But why start ThreadFunc in a separate std::thread anyway? Just use std::async which will return a future which will execute your ThreadFunci.e. TestFlow::DoWork.
You probably got the abort because you where trying to join, nonjoinable threads, or because you didn't join some explicit (when moving a new one, in the destructor of the old std::thread) at the position
workerThreads[readerCounter] = std::thread(&TestFlow::DoWork, testFlowObjects.back());
Background/problem
If you want to still use a std::thread you have to do the communication and waiting between the threads by yourself. That implies tasks and problems of many kind (stopping, joining, waiting, thread pooling).
The workarounds you linked assumes, you have some other means to terminate a thread. (by communication)
Related
Due to fixed requirements, I need to execute some code in a specific thread, and then return a result. The main-thread initiating that action should be blocked in the meantime.
void background_thread()
{
while(1)
{
request.lock();
g_lambda();
response.unlock();
request.unlock();
}
}
void mainthread()
{
...
g_lambda = []()...;
request.unlock();
response.lock();
request.lock();
...
}
This should work. But it leaves us with a big problem: background thread needs to start with response mutex locked, and main-thread needs to start with request mutex locked...
How can we accomplish that? I cant think of a good way. And isnt that an anti-pattern anyways?
Passing tasks to background thread could be accomplished by a producer-consumer queue. Simple C++11 implementation, that does not depend on 3rd party libraries would have std::condition_variable which is waited by the background thread and notified by main thead, std::queue of tasks, and std::mutex to guard these.
Getting the result back to main thread can be done by std::promise/std::future. The simplest way is to make std::packaged_task as queue objects, so that main thread creates packaged_task, puts it to the queue, notifies condition_variable and waits on packaged_task's future.
You would not actually need std::queue if you will create tasks by one at once, from one thread - just one std::unique_ptr<std::packaged_task>> would be enough. The queue adds flexibility to simultaneosly add many backround tasks.
I'm trying to synchonise a set of threads. These threads sleep most of the time, waking up to do their scheduled job. I'm using std::thread for them.
Unfortunately, when I terminate the application threads prevent it from exiting. In C# I can make a thread to be background so that it will be termianted on app exit. It seems to me that equavalint feature is not availabe at C++.
So I decided to use a kind of event indicator, and make the threads to wake up when the app exits. Standard C++11 std::condition_variable requires a unique lock, so I cannot use it, as I need both threads to wake up at the same time (they do not share any resources).
Eventually, I decided to use WinApi's CreateEvent + SetEvent+WaitForSingleObject in order to solve the issue.
I there a way to achieve the same behavior using just c++11?
Again, what do I want:
a set of threads are working independently and usually are asleep
for a particular period (could be different for different threads;
all threds check a variable that is availabe for all of them whether
it is a time to stop working (I call this variable IsAliva).
Actually all threads are spinning in loop like this:
while (IsAlive) {
// Do work
std::this_thread::sleep_for(...);
}
threads must be able to work simultaneously, not blocking each other;
when the app is closed and event is risen and it makes the thread to
wake up right now, no matter the timeout;
waken up, it checks the
IsAlive and exits.
yes you can do this using standard c++ mechanisms of condition variables, a mutex and a flag of somekind
// Your class or global variables
std::mutex deathLock;
std::condition_variable deathCv;
bool deathTriggered = false;
// Kill Thread runs this code to kill all other threads:
{
std::lock_guard<std::mutex> lock(deathLock);
deathTriggered = true;
}
deathCv.notify_all();
// You Worker Threads run this code:
while(true)
{
... do work
// Now wait for 1000 milliseconds or until death is triggered:
std::unique_lock<std::mutex> lock(deathLock);
deathCv.wait_for(lock, std::chrono::milliseconds(1000), [](){return deathTriggered;});
// Check for death
if(deathTriggered)
{
break;
}
}
Note that this runs correctly in the face of death being triggered before entering the condition. You could also use the return value from wait_for but this way is easier to read imo. Also, whilst its not clear, multiple threads sleeping is fine as the wait_for code internally unlocks the unique_lock whilst sleeping and reacquires it to check the condition and also when it returns.
Finally, all the threads do wake up 'at the same time' as whilst they're serialised in checking the bool flag, this is only for a few instructions then they unlock the lock as they break out of the loop. It would be unnoticeable.
In c++11, you should be able to detach() a thread, so that it will be treated as a Daemon thread, which means the thread will be automatically stopped if the app terminates.
I'm new to thread in C++ 11. I have two threads and I want to make them start at the exact same time. I could think of two ways of doing it (as below). However, it seems that none of them work as I expected. They are start one thread before launching another. Any hint would be appreciated! Another question is I'm working on a threaded queue. So I would have two consumers and four producers. Is the following code for consumer the right way to go? Is there any reference that anyone can provide?
for(int i = 1; i <= 2; i++)
auto c = async(launch::async, consumer, i);
auto c1 = async(launch::async, consumer, 1);
auto c2 = async(launch::async, consumer, 2);
What the other answers said about it not being possible to guarantee that two threads start at the same time is true. Still, if you want to come close there are different ways to do that.
One way is to use a set of std::promises to indicate when everything is ready. Each thread sets a promise to indicate that it's ready and then waits on a (copy of a) std::shared_future obtained from a third std::promise; the main thread waits for all the promises from all the threads to be set and then triggers the threads to go. This ensures that each thread has started and is just before the chunk of code that should be run concurrently.
std::promise<void> go, ready1, ready2; // Promises for ready and go signals
std::shared_future<void> ready(go.get_future()); // Get future for the go signal
std::future<void> done1, done2; // Get futures to indicate that threads have finished
try
{
done1 = std::async(std::launch::async,
[ready, &ready1]
{
ready1.set_value(); // Set this thread's ready signal
ready.wait(); // Wait for ready signal from main thread
consumer(1);
});
done2 = std::async(std::launch::async,
[ready, &ready2]
{
ready2.set_value(); // Set this thread's ready signal
ready.wait(); // Wait for ready signal from main thread
consumer(2);
});
// Wait for threads to ready up
ready1.get_future().wait();
ready2.get_future().wait();
// Signal threads to begin the real work
go.set_value();
// Wait for threads to finish
done1.get();
done2.get();
}
catch (...)
{
go.set_value(); // Avoid chance of dangling thread
throw;
}
Note: most of this answer was copied from "C++ Concurrency in Action" by Anthony Williams (pages 311-312), but I adapted the code to fit the example in the question.
to launch two threads simultaneously I see no other way than first launching 2 threads the classic way, then blocking them using a barrier to synchronize them, but the release broadcast has no guarantee of re-scheduling them both at the same time.
Alternatively you could spin check a global time counter or something but even then...
It is impossible to start two threads at one time. The CPU can only do one thing at a time. It threads by stopping one thread, saving register states, and restoring those of the other thread, and executing that thread for a while. Think of it more like this (though not exactly how it works).
hey cpu, i want to do two things at once, eat apples and bananas
CPU says
ok, well, heres what we will do. Eat a bit of an apple
now, eat some banana
repeat..
Therefore, you can start them in close proximity, but not at the exact same time.
I am working on a networking program using C++ and I'd like to implement a pthread pool. Whenever, I receive an event from the receive socket, I will put the data into the queue in the thread pool. I am thinking about creating 5 separate threads and will consistently check the queue to see if there is anything incoming data to be done.
This is quite straight forward topic but I am not a expert so I would like to hear anything that might help to implement this.
Please let me know any tutorials or references or problems I should aware.
Use Boost.Asio and have each thread in the pool invoke io_service::run().
Multiple threads may call
io_service::run() to set up a pool of
threads from which completion handlers
may be invoked. This approach may also
be used with io_service::post() to use
a means to perform any computational
tasks across a thread pool.
Note that all threads that have joined
an io_service's pool are considered
equivalent, and the io_service may
distribute work across them in an
arbitrary fashion.
Before I start.
Use boost::threads
If you want to know how to do it with pthread's then you need to use the pthread condition variables. These allow you to suspend threads that are waiting for work without consuming CPU.
When an item of work is added to the queue you signal the condition variable and one pthread will be released from the condition variable thus allowing it to take an item from the queue. When the thread finishes processing the work item it returns back to the condition variable to await the next piece of work.
The main loop for the threads in the loop should look like this;
ThreadWorkLoop() // The function that all the pool threads run.
{
while(poolRunnin)
{
WorkItem = getWorkItem(); // Get an item from the queue. This suspends until an item
WorkItem->run(); // is available then you can run it.
}
}
GetWorkItem()
{
Locker lock(mutex); // RAII: Lock/unlock mutex
while(workQueue.size() == 0)
{
conditionVariable.wait(mutex); // Waiting on a condition variable suspends a thread
} // until the condition variable is signalled.
// Note: the mutex is unlocked while the thread is suspended
return workQueue.popItem();
}
AddItemToQueue(item)
{
Locker lock(mutex);
workQueue.pushItem(item);
conditionVariable.signal(); // Release a thread from the condition variable.
}
Have the receive thread to push the data on the queue and the 5 threads popping it. Protect the queue with a mutex and let them "fight" for the data.
You also want to have a usleep() or pthread_yield() in the worker thread's main loop
You will need a mutex and a conditional variable. Mutex will protect your job queue and when receiving threads add a job to the queue it will signal the condition variable. The worker threads will wait on the condition variable and will wake up when it is signaled.
Boost asio is a good solution.
But if you dont want to use it (or cant use it for whatever reasons) then you'll probably want to use a semaphore based implementation.
You can find a multithreaded queue implementation based on semaphores that I use here:
https://gist.github.com/482342
The reason for using semaphores is that you can avoid having the worker threads continually polling, and instead have them woken up by the OS when there is work to be done.
I'm working on a C/C++ networking project and am having difficulties synchronizing/signaling my threads. Here is what I am trying to accomplish:
Poll a bunch of sockets using the poll function
If any sockets are ready from the POLLIN event then send a signal to a reader thread and a writer thread to "wake up"
I have a class called MessageHandler that sets the signals mask and spawns the reader and writer threads. Inside them I then wait on the signal(s) that ought to wake them up.
The problem is that I am testing all this functionality by sending a signal to a thread yet it never wakes up.
Here is the problem code with further explanation. Note I just have highlighted how it works with the reader thread as the writer thread is essentially the same.
// Called once if allowedSignalsMask == 0 in constructor
// STATIC
void MessageHandler::setAllowedSignalsMask() {
allowedSignalsMask = (sigset_t*)std::malloc(sizeof(sigset_t));
sigemptyset(allowedSignalsMask);
sigaddset(allowedSignalsMask, SIGCONT);
}
// STATIC
sigset_t *MessageHandler::allowedSignalsMask = 0;
// STATIC
void* MessageHandler::run(void *arg) {
// Apply the signals mask to any new threads created after this point
pthread_sigmask(SIG_BLOCK, allowedSignalsMask, 0);
MessageHandler *mh = (MessageHandler*)arg;
pthread_create(&(mh->readerThread), 0, &runReaderThread, arg);
sleep(1); // Just sleep for testing purposes let reader thread execute first
pthread_kill(mh->readerThread, SIGCONT);
sleep(1); // Just sleep for testing to let reader thread print without the process terminating
return 0;
}
// STATIC
void* MessageHandler::runReaderThread(void *arg) {
int signo;
for (;;) {
sigwait(allowedSignalsMask, &signo);
fprintf(stdout, "Reader thread signaled\n");
}
return 0;
}
I took out all the error handling I had in the code to condense it but do know for a fact that the thread starts properly and gets to the sigwait call.
The error may be obvious (its not a syntax error - the above code is condensed from compilable code and I might of screwed it up while editing it) but I just can't seem to find/see it since I have spent far to much time on this problem and confused myself.
Let me explain what I think I am doing and if it makes sense.
Upon creating an object of type MessageHandler it will set allowedSignalsMask to the set of the one signal (for the time being) that I am interested in using to wake up my threads.
I add the signal to the blocked signals of the current thread with pthread_sigmask. All further threads created after this point ought to have the same signal mask now.
I then create the reader thread with pthread_create where arg is a pointer to an object of type MessageHandler.
I call sleep as a cheap way to ensure that my readerThread executes all the way to sigwait()
I send the signal SIGCONT to the readerThread as I am interested in sigwait to wake up/unblock once receiving it.
Again I call sleep as a cheap way to ensure that my readerThread can execute all the way after it woke up/unblocked from sigwait()
Other helpful notes that may be useful but I don't think affect the problem:
MessageHandler is constructed and then a different thread is created given the function pointer that points to run. This thread will be responsible for creating the reader and writer threads, polling the sockets with the poll function, and then possibly sending signals to both the reader and writer threads.
I know its a long post but do appreciate you reading it and any help you can offer. If I wasn't clear enough or you feel like I didn't provide enough information please let me know and I will correct the post.
Thanks again.
POSIX threads have condition variables for a reason; use them. You're not supposed to need signal hackery to accomplish basic synchronization tasks when programming with threads.
Here is a good pthread tutorial with information on using condition variables:
https://computing.llnl.gov/tutorials/pthreads/
Or, if you're more comfortable with semaphores, you could use POSIX semaphores (sem_init, sem_post, and sem_wait) instead. But once you figure out why the condition variable and mutex pairing makes sense, I think you'll find condition variables are a much more convenient primitive.
Also, note that your current approach incurs several syscalls (user-space/kernel-space transitions) per synchronization. With a good pthreads implementation, using condition variables should drop that to at most one syscall, and possibly none at all if your threads keep up with each other well enough that the waited-for event occurs while they're still spinning in user-space.
This pattern seems a bit odd, and most likely error prone. The pthread library is rich in synchronization methods, the one most likely to serve your need being in the pthread_cond_* family. These methods handle condition variables, which implement the Wait and Signal approach.
Use SIGUSR1 instead of SIGCONT. SIGCONT doesn't work. Maybe a signal expert knows why.
By the way, we use this pattern because condition variables and mutexes are too slow for our particular application. We need to sleep and wake individual threads very rapidly.
R. points out there is extra overhead due to additional kernel space calls. Perhaps if you sleep > N threads, then a single condition variable would beat out multiple sigwaits and pthread_kills. In our application, we only want to wake one thread when work arrives. You have to have a condition variable and mutex for each thread to do this otherwise you get the stampede. In a test where we slept and woke N threads M times, signals beat mutexes and condition variables by a factor of 5 (it could have been a factor of 40 but I cant remember anymore....argh). We didn't test Futexes which can wake 1 thread at a time and specifically are coded to limit trips to kernel space. I suspect futexes would be faster than mutexes.