First, let's know what is being done.
system($shell_command)
not suitable for
system({ "/bin/sh" } "/bin/sh", "-c", $shell_command)
if the shell command does not contain shell metacharacters, but spaces, in this case
system($shell_command)
not suitable for
my @cmd = split(' ', $shell_command); system({ $cmd[0] } @cmd)
Thus,
system("child.pl 'dummy'") is short for system({ "/bin/sh" } "/bin/sh", "-c", "child.pl 'dummy'") system("child.pl") is short for system({ "child.pl" } "child.pl") system("bash -c child.pl") is short for system({ "bash" } "bash", "-c", "child.pl") system("sh -c child.pl") is short for system({ "sh" } "sh", "-c", "child.pl")
It should be noted that bash replaces itself with child.pl instead of propagating it in a separate process in this particular case. This makes child.pl direct child of parent.pl in the third case (as in the second case).
Secondly, let's know what Ctrl-C does.
When Ctrl-C is pressed, the terminal sends SIGINT to each process that has this terminal as the control terminal. In other words, SIGINT is sent to each session process.
As you can see, adding system("ps -o pid,ppid,pgrp,sid,cmd"); in child.pl , there are three or four processes in our session, depending on the test case.
child.pl : child.pl handles SIGINT. He is not killed by him.- The shell started by
parent.pl in test cases 1 and 4: the shell is killed by SIGINT. parent.pl : system makes the equivalent of local $SIG{INT} = 'IGNORE'; so it ignores sigint.- Login shell starting
parent.pl : it ignores SIGINT, but I don't know why. I assume this is an interactive shell.
So this is what you are observing:
- When the (direct) child element of
parent.pl is child.pl [Test Examples 2 and 3], the child element ( child.pl ) does not die from SIGINT, since it processes SIGINT. - When the (direct) child element of
parent.pl is the shell [Test cases 1 and 4], the child element (shell) dies from SIGINT because non-interactive shells do not process / ignore SIGINT.
ikegami
source share