After the test-set has completed, the process executes java.lang.System.exit(0) which starts shutdown hooks. At this point the process may run next 30 seconds until all non daemon Threads die. After the period of time has elapsed, the process kills itself by java.lang.Runtime.halt(0).
The master process sends NOOP command to a forked JVM every 10 seconds. Forked JVM is waiting for the command every 20 seconds. If the master process is killed (received SIGKILL signal) or shutdown (pressed CTRL+C, received SIGTERM signal), forked JVM is killed after timing out waiting period.
After the master process of the build is shutdown by sending SIGTERM signal or pressing CTRL+C, the master process immediately sends SHUTDOWN command to every forked JVM. By default (configuration parameter shutdown=testset) forked JVM would not pick up a new test which means that the current test may still continue to run. The SIGTERM signal triggers Java shutdownhook which executes java.lang.Process.destroy() in the forked JVM (not always reliable depending on VM and OS). The parameter shutdown can be configured with other two values exit and kill. Using exit forked JVM executes java.lang.System.exit(1) after the master process has received SIGTERM. Using kill the JVM executes java.lang.Runtime.halt(1), example:
<project> [...] <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-failsafe-plugin</artifactId> <version>2.19.1</version> <configuration> <shutdown>kill</shutdown> </configuration> </plugin> </plugins> </build> [...] </project>