How is it possible that kill -9 for a process on Linux has no effect?
As noted in comments to the OP, a process status (STAT
) of D
indicates that the process is in an "uninterruptible sleep" state. In real-world terms, this generally means that it's waiting on I/O and can't/won't do anything - including dying - until that I/O operation completes.
Processes in a D
state will normally only be there for a fraction of a second before the operation completes and they return to R
/S
. In my experience, if a process gets stuck in D
, it's most often trying to communicate with an unreachable NFS or other remote filesystem, trying to access a failing hard drive, or making use of some piece of hardware by way of a flaky device driver. In such cases, the only way to recover and allow the process to die is to either get the fs/drive/hardware back up and running so the I/O can complete or to give up and reboot the system. In the specific case of NFS, the mount may also eventually time out and return from the I/O operation (with a failure code), but this is dependent on the mount options and it's very common for NFS mounts to be set to wait forever.
This is distinct from a zombie process, which will have a status of Z
.
Consequences of using kill -9 for node processes?
It doesn't give the process a chance to cleanly:
1) shut down socket connections
2) clean up temp files
3) inform its children that it is going away
4) reset its terminal characteristics
These are the bad consequences of what can happen when you use kill -9
. You should only use kill -9
as a last resort if all else has failed.
And to the second question, because kill -9
will kill the process even if it is in the middle of doing something while kill
will shutdown the process after a clean exit.
kill -9 doesn't work
Process will get the KILL signal (all signals behave in the same way) only and only when it is in "userspace". If it is in kernelspace (for example waiting for a NFS share to deliver data read from file), it will not get the signal (the signal will wait until process returns to userspace, it will not get lost).
Most NFSD's have some options regarding this, it can return from read with failure status if it times out. This will cause data loss (as will the other option..) because not all programs check for all read()
results.
Processes can not ignore/cancel KILL signal, it's notification only and gives a chance to save any necessary data.
when a process is killed is this information recorded anywhere?
If your Linux kernel is compiled with the process accounting (CONFIG_BSD_PROCESS_ACT
) option enabled, you can start recording process accounting info using the accton(8)
command and use sa(8)
to access the recorded info. The recorded information includes the 32 bit exit code which includes the signal number.
(This stuff is not widely known / used these days, but I still remember it from the days of 4.x Bsd on VAXes ...)
How to kill zombie process
A zombie is already dead, so you cannot kill it. To clean up a zombie, it must be waited on by its parent, so killing the parent should work to eliminate the zombie. (After the parent dies, the zombie will be inherited by pid 1, which will wait on it and clear its entry in the process table.) If your daemon is spawning children that become zombies, you have a bug. Your daemon should notice when its children die and wait
on them to determine their exit status.
An example of how you might send a signal to every process that is the parent of a zombie (note that this is extremely crude and might kill processes that you do not intend. I do not recommend using this sort of sledge hammer):
# Don't do this. Incredibly risky sledge hammer!
kill $(ps -A -ostat,ppid | awk '/[zZ]/ && !a[$2]++ {print $2}')
How to kill a process based on its argument
If you're on linux, use pkill with the string with args of the process you want to kill. The -f flag specifies to match the full string and args to the running process.
pkill -f "rsync -av /456"
Any other flavor of *nix, use ps with flags, pipe to grep, pipe to awk to pull the process id, then pipe to kill.
How to create a process which kills it's parent and making some actions after that
Unfortunately, no one provides answer. So looks like it's not possible to implement it via the standard process model, but I solved it via running the separate daemon (background service) which is triggered by the main process, kill it and replaces with the new updated version and making it up and running again.
Related Topics
Rename Part of File Name Based on Exact Match in Contents of Another File
Linux Script to Automate Ftp Operation
If I Have a Process, and I Clone It, Is the Pid the Same
String Comparison Not Working Properly
While Do Loop and Variables in a Bash Script
Python Socket.Error: [Errno 13] Permission Denied
Insert New Line to Bash Prompts
Splitting Gzipped Logfiles Without Storing the Ungzipped Splits on Disk
Execute Command Line and Return Command Output
Best Posix Way to Determine If a Filesystem Is Mounted Read Only
Boost with Qt Creator and Linux
Makefile with Multiple Targets
Bash: Best Architecture for Reading from Two Input Streams
How to Remove X Bytes from the End of a Large File Without Reading the Whole File