I currently start an executable on my mobile using adb shell (binary needs the "shell" user permissions). I want to keep the process running in the background for as long as possible, but the process dies every time I disconnect the USB cord.
The testing device's OS is an unofficial Version of LineageOS / Android 8.1.
I have tried:
- starting the executable with all combinations of "nohup" and "> /dev/null 2> /dev/null < /dev/null &"
- to catch and handle every possible signal in the executable itself
- to fork off the process as a daemon
- all of the above combined
My current code is the following, compiled in a standard NDK-project with the CMake configuration "add_executable(libDaemonize.so Daemonize.c)" and executed in adb shell with "nohup /data/app/org.app.name/lib/arm/libDaemonize.so > /dev/null 2> /dev/null < /dev/null &". The "lib***.so" name is necessary to automatically pack the binary into the apk and install it on the device with executable permissions.
/*Based on https://stackoverflow.com/a/17955149/11250128*/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <syslog.h>
void INThandler(int);
static void skeleton_daemon()
{
pid_t pid;
/* Fork off the parent process */
pid = fork();
/* An error occurred */
if (pid < 0)
exit(EXIT_FAILURE);
/* Success: Let the parent terminate */
if (pid > 0) {
syslog (LOG_NOTICE, "From starter: PID: %d, PPID: %d\n", getpid(), getppid());
exit(EXIT_SUCCESS);
}
/* On success: The child process becomes session leader */
if (setsid() < 0)
exit(EXIT_FAILURE);
/* Catch, ignore and handle ALL signals */
int i;
for(i=1; i<32; i++) {
signal(i, INThandler);
}
/* Fork off for the second time*/
pid = fork();
/* An error occurred */
if (pid < 0)
exit(EXIT_FAILURE);
/* Success: Let the parent terminate */
if (pid > 0)
exit(EXIT_SUCCESS);
/* Set new file permissions */
umask(0);
/* Change the working directory to the root directory */
/* or another appropriated directory */
chdir("/");
/* Close all open file descriptors */
int x;
for (x = sysconf(_SC_OPEN_MAX); x>=0; x--)
{
close (x);
}
/* Open the log file */
openlog ("testdaemon", LOG_PID, LOG_DAEMON);
}
int main()
{
skeleton_daemon();
while (1)
{
syslog (LOG_NOTICE, "Daemon running. PID: %d, PPID: %d\n", getpid(), getppid());
sleep (1);
}
syslog (LOG_NOTICE, "Daemon terminated.");
closelog();
return EXIT_SUCCESS;
}
/*Define signal handlers to find out what signal kills us */
void INThandler(int sig)
{
syslog(LOG_CRIT, "Daemon received Signal %d", sig);
}
The calls all succeed and work as expected (e.G. the daemon taking init/pid 1 as a parent), but as soon as the USB cord is disconnected, the application stops printing to syslog.
My best guess is that the Android system actively kills the process, but neither the Adbd logs (activated via "setprop persist.adb.trace_mask") nor after my search in the Adb source I found any evidence for this.
I feel like I miss something obvious. Thanks for your ideas.