I am programming a tree of processes in Linux and I wonder if there is any signal that can be used just to send from A process to B process without affecting B process.
For example, assume B_pid is the process B's ID, if process A calls kill(B_pid, SIGSTOP); then A will pause B. What I am looking for is a signal, let's say SIGNOTHING, that when A calls kill(B_pid, SIGNOTHING), then it just simply sends a message to B rather than doing something to both B and the system.
SIGUSR1 and SIGUSR2 are designed for that purpose.
If you invoke the following command on your shell:
kill -l
you get a full list of signals available for your system.
Most of the signals can be used to simply "receive" them on the target side. BUT: Most signals are also used by the system itself to tell the application that something special happened, like SIGSEGV. So it makes no sense to use signals, which have a fixed meaning as they are used to communicate from kernel/OS to the application.
For user signals, you have two signals reserved, which can be used for everything you like: SIGUSR1 and SIGUSR2.
Not all Unix systems have these signals! So first take a look which signals can be used on your current system!
Additional hint:
Check you signal handlers and the context on which they are running. On some implementations it is not allowed to call non-reentrant functions from the context of the handler. So it is maybe more useful to communicate via a pipe or any other IPC method.
There are signals that are meant for use for user programs. From man signal:
The signals SIGKILL and SIGSTOP cannot be caught, blocked, or ignored.
SIGSTOP will always stop the program and SIGKILL will always terminate the program.
There are two user-defined signals commonly used for signal communication between processes:
SIGUSR1 ... User-defined signal 1
SIGUSR2 ... User-defined signal 2
And there is also a whole range of real-time signals for use as user-defined signals between SIGRTMIN and SIGRTMAX, that have to be at least 8 signals (ie. SIGRTMAX - SIGRTMIN >= 8) and linux supports 33 signals. These are all for use for user-application to do anything it desires.
Basically each signal in Linux has a action associated with it.
Man page of signal:
Signal dispositions
Each signal has a current disposition, which determines how the
process behaves when it is delivered the signal.
The entries in the "Action" column of the table below specify the
default disposition for each signal, as follows:
Term Default action is to terminate the process.
Ign Default action is to ignore the signal.
Core Default action is to terminate the process and dump core (see
core(5)).
Stop Default action is to stop the process.
Cont Default action is to continue the process if it is currently
stopped.
SIGSTOP
SIGSTOP P1990 Stop Stop process
A process can change the disposition of a signal using sigaction(2)
or signal(2). (The latter is less portable when establishing a
signal handler; see signal(2) for details.) Using these system
calls, a process can elect one of the following behaviors to occur on
delivery of the signal: perform the default action; ignore the
signal; or catch the signal with a signal handler, a programmer-
defined function that is automatically invoked when the signal is
delivered.
You can define your own signal handler and define the behavior of your process.
Note: SIGKILL and SIGSTOP cannot be caught
Related
Platform is Linux/POSIX.
The signal is sent to a whole process, not a specific thread.
No signal is set to blocked, all default.
The process is multi-thread process.
From what I've googled, a signal may be handled by a random thread.
And when that signal's handler is executing, it's temporarily blocked until handler returns.
QUESTION: Multiple signals of different types reached simultaneously. Do their handler execute simultaneously on multiple thread or all of them go to one randomly picked thread (SUB-QUESTION: in this case a handler could interrupt another handler's execution started previously, so there could be a interrupt stack?) ? Or mixed? For instance there are 3 type of signals received but only 2 thread free (this is actually the first case).
EXAMPLE: SIGHUP, SIGINT, SIGTERM reached almost simultaneously. The program has two available thread to dispatch signal handler execution.
SIDE-QUESTION: If signal handlers run in parallel, I'll have to use mutex to synchronize them properly. Otherwise 'volatile sig_atomic_t' would be enough, right?
Expected: all signals go to one thread (randomly picked) despite of their different signal types, I haven't seen an example of using mutexes and atoms to synchronize signal handlers.
Your understanding is correct - unless a signal was directed
to a specific thread, there's no guarantee which thread will handle a signal.
See POSIX's Signal Generation and Delivery and pthreads(7):
POSIX.1 distinguishes the notions of signals that are directed
to the process as a whole and signals that are directed to
individual threads. According to POSIX.1, a process-directed
signal (sent using kill(2), for example) should be handled by
a single, arbitrarily selected thread within the process.
So it may be delivered & handled by the same thread that's currently handling another signal (in that case, the previous handler may be interrupted by the new signal). Or may be delivered to another signal.
You can block other signals while one is being handled using sa_mask field
of sigaction to avoid a signal handler being interrupted.
SIDE-QUESTION: If signal handlers run in parallel, I'll have to use mutex to synchronize them properly. Otherwise 'volatile sig_atomic_t' would be enough, right?
You almost certainly don't want to use mutex in a signal handler. There are only few functions that can be safely called from a signal handler (you can only call the functions that are async-signal-safe).
See signal-safty for more information.
If you can use volatile sig_atomic_t for whatever the purpose (do you need to co-ordinate execution of different signal handlers?), it should be preferred.
Expected: all signals go to one thread (randomly picked) despite of their different signal types, I haven't seen an example of using mutexes and atoms to synchronize signal handlers.
This is commonly done by blocking signals that you're interested in from main and fetching/handling them in a specific thread. See pthread_sigmask which also has an example on how to implement this.
I'm currently learning how signals really works in POSIX-systems. Signals such as SIGTERM can be caught and handled with custom handlers, this means that the kernel propagates the signal to the process itself. On the other hand SIGKILL is not catchable and cannot be handled firstly because it is its main purpose - kill the process. But I'm wondering does this means that the SIGKILL is not even propagated to the process ? I mean if the users will send kill -9 to some process using terminal the kernel will immediately purge that process without even forwarding the signal to it, or the signal will still be forwarded to the process but with the exception that we cannot add a custom handler to it? Sorry, if you consider this question dummy! I'm just starting with POSIX systems
some signals can catch and we name those catchable signals and some are uncatchable. The signals SIGKILL and SIGSTOP cannot be caught, blocked, or ignored.
You can see a complete list of signals and appropriate action here.
In Linux 2.6, I would like my process to catch both SIGHUP and SIGTERM in order to exit orderly.
When the node shuts down, logs show that it will handle either SIGHUP (the parent process receives SIGTERM) or SIGTERM first.
My question is: is there a possibility that the handlers for these signals are called concurrently? or the kernel triggers one after the other?
Depending on your code architecture you could enforce synchronous reading of signals preventing any concurrency issues. You could use signalfd and then read from that fd whenever you want to check on any outstanding signals. If you need them to behave in their asynchronous default with a signal handler I think you have to be prepared for your signal handler to be potentially interrupted.
man signalfd
In Asynchronous signals to a process, the Linux kernel send signals with a system call to target process structure and when context of the process is switched to RUN state, signals are handled by root thread and block signals on all other threads. Since the stack space is different for each thread each signal can be handled at a time(Correct if am wrong).
How I would go about capturing/intercepting signals sent to another process from my own process? Willing to use C, Ruby, or any Linux package.
You can write a library wrapper that will replace system signal/sigaction calls to intercept setting of the signal handler and set your own handlers. On received signal, you can do your job and call user handler later. Use LD_PRELOAD to replace system signal/sigaction routines by your own.
I think that the ptrace(2) system call is what you want. From the manual: "While being traced, the child will stop each time a signal is delivered, even if the signal is being ignored. (The exception is SIGKILL, which has its usual effect.) The parent will be notified at its next wait(2) and may inspect and modify the child process while it is stopped. The parent then causes the child to continue, optionally ignoring the delivered signal (or even delivering a different signal instead)."
The man page for pthreads mentions:
POSIX.1 also requires that threads share a range of other attributes
(i.e., these attributes are process-wide rather than per-thread):
...
- signal dispositions
...
What do "signal dispositions" mean?
I signal disposition is the action a process takes when a signal is delivered. Each signal has a disposition. There are defaults.
From signal(7):
Signal Dispositions
Each signal has a current disposition, which determines how the process
behaves when it is delivered the signal.
[Dispositions are:]
Term Default action is to terminate the process.
Ign Default action is to ignore the signal.
Core Default action is to terminate the process and dump core (see core(5)).
Stop Default action is to stop the process.
Cont Default action is to continue the process if it is currently stopped.
[...]
The signal disposition is a per-process attribute: in a multithreaded
application, the disposition of a particular signal is the same for all
threads.
The disposition of a signal is how it is handled.
It might be ignored
It might be handled using the default response (which depends on the signal)
stop
exit
exit with core dump
ignore
It might be handled by a user-defined signal handler
There can also be issues of signals masked while the signal handler is called, and so on.
This means how Unix process reacts to signals. See signal(7).