Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Posix select()/poll() and pthread IPC

This is kind of generic question - however I met this problem several times already and I still haven't found the best possible solution.

Let's imagine you have program (e.g. HTTP application server) that is multithreaded and that communicates over sockets (TCP, Unix, ...). Main thread is using asynchronous IO and select() or poll() POSIX calls to dispatch traffic from/to sockets. There are also worker threads that process requests and provides responses. To send response back to the client, worker thread synchronises with main thread (that polls) 'somehow'. Core of the questions is 'how' - in terms of what is efficient. I can use pipe() - socket based IPC mechanism - but this seems to me as quite huge overhead. I tend to use some pthread IPC techniques like mutex, condition variables etc. … but these will not work with select() or poll().

Is there a common technique in POSIX (and surroundings) that address this conflict? I guess on Windows there is WaitForMultipleObjects() function that allows that.

Example program is crafted to illustrate an issue, I know that I can design master/worker pattern in a different way but this is not what I'm asking for. I have other cases where I'm in the same situation.

like image 751
Ales Teska Avatar asked Jun 16 '14 11:06

Ales Teska


People also ask

What is Posix thread in C?

The POSIX thread libraries are a standards based thread API for C/C++. It allows one to spawn a new concurrent process flow. It is most effective on multi-processor or multi-core systems where the process flow can be scheduled to run on another processor thus gaining speed through parallel or distributed processing.

What is the Posix threads P threads model?

POSIX Threads, commonly known as pthreads, is an execution model that exists independently from a language, as well as a parallel execution model. It allows a program to control multiple different flows of work that overlap in time.

What function creates a Posix thread?

In a Unix/Linux operating system, the C/C++ languages provide the POSIX thread(pthread) standard API(Application program Interface) for all thread related functions. It allows us to create multiple threads for concurrent process flow.

Which API is used for Posix thread creation?

POSIX Threads in OS : The POSIX thread libraries are a C/C++ thread API based on standards. It enables the creation of a new concurrent process flow.


1 Answers

You could use a signal to poke the worker thread, which will interrupt the select() call and return EINTR. This gets even easier to do with pselect().

For this to work:

  1. decide on a signal (or allocate a real-time signal)
  2. attach an empty handler function to it (if the signal were ignored, the system call would be automatically restarted)
  3. block the signal, at least in the worker thread.
  4. use the signal mask argument in pselect() to unblock the signal while waiting.

Between threads, you can use pthread_kill to deliver the signal to the worker thread specifically. When another process should send the signal, you can either make sure the signal is blocked in all but the worker thread (so it will be delivered there), or use the signal handler to find out whether the signal was sent to the worker thread, and use pthread_kill to forward it explicitly (the worker thread still doesn't need to do anything in the signal handler).

Due to laziness on my part, I don't have a source code viewer online, but you can clone the LibreVISA git tree, and take a look at src/messagepump.cpp, where this method is used to poke the worker thread after another thread added a file descriptor to the watch list.

like image 193
Simon Richter Avatar answered Sep 24 '22 03:09

Simon Richter