With default signal handling, I observe that when a child process keeps in D-state, I can terminate it parent process, and then the D-state child process would become a child of init (pid-1).
Test Environment
2 x Red Hat Enterprise Linux 6.7
|
-- NFS Server
|
-- NFS Client (Run below code in this server)
Example Code
[root@rhel674 tmp]# cat zstate1.c
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <syslog.h>
int main()
{
FILE *pFile;
char buffer[256];
pid_t pid;
int returnstatus;
pid = fork();
/* Failed to fork */
if (pid < 0)
exit(EXIT_FAILURE);
/* parent */
if (pid > 0){
waitpid(pid, &returnstatus, 0);
printf ("child process return: %d \n", returnstatus);
}
/* child */
if (pid == 0) {
pFile=fopen("/mnt/nfs/testfile", "r+");
while(1){
fprintf (pFile, "test");
}
}
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <syslog.h>
int main()
{
FILE *pFile;
char buffer[256];
pid_t pid;
int returnstatus;
pid = fork();
/* Failed to fork */
if (pid < 0)
exit(EXIT_FAILURE);
/* parent */
if (pid > 0){
waitpid(pid, &returnstatus, 0);
printf ("child process return: %d \n", returnstatus);
}
/* child */
if (pid == 0) {
pFile=fopen("/mnt/nfs/testfile", "r+");
while(1){
fprintf (pFile, "test");
}
}
return 0;
}
Compile this code with below command:
# gcc -Wall -o zstate1 zstate1.c
Test Steps
1. In NFS Client, run the above program:
# mount -t nfs <nfs-server>:<nfs-share> /mnt/nfs
# /tmp/zstate1
# /tmp/zstate1
2. After a while, poweroff (shut it down forcefully ) NFS Server.
Then we would see a child process stays in D-state:
[root@HA6-0 ~]# ps aux | grep zstate
root 32347 0.0 0.0 3920 340 pts/0 S+ 09:02 0:00 /tmp/zstate1
root 32348 27.2 0.0 4180 408 pts/0 D+ 09:02 0:01 /tmp/zstate1
root 32354 0.0 0.0 103308 848 pts/1 S+ 09:02 0:00 grep zstate
root 32347 0.0 0.0 3920 340 pts/0 S+ 09:02 0:00 /tmp/zstate1
root 32348 27.2 0.0 4180 408 pts/0 D+ 09:02 0:01 /tmp/zstate1
root 32354 0.0 0.0 103308 848 pts/1 S+ 09:02 0:00 grep zstate
3. Kill the parent, and we could see the parent exits, only the D-state child remains.
[root@HA6-0 ~]# kill 32347
[root@HA6-0 ~]# ps aux | grep zstate
root 32348 7.1 0.0 4180 408 pts/0 D 09:02 0:01 /tmp/zstate1
root 32361 0.0 0.0 103308 848 pts/1 S+ 09:02 0:00 grep zstate
[root@HA6-0 ~]# ps aux | grep zstate
root 32348 7.1 0.0 4180 408 pts/0 D 09:02 0:01 /tmp/zstate1
root 32361 0.0 0.0 103308 848 pts/1 S+ 09:02 0:00 grep zstate
4. The parent of the D-state child becomes init (pid-1)
[root@HA6-0 ~]# cat /proc/32348/status
Name: zstate1
State: D (disk sleep)
Tgid: 32348
Pid: 32348
PPid: 1
Name: zstate1
State: D (disk sleep)
Tgid: 32348
Pid: 32348
PPid: 1