From 08aca403161f4311c668f210feaf78fca86544ac Mon Sep 17 00:00:00 2001 From: Sergey Popov Date: Tue, 15 Nov 2011 17:53:12 +0400 Subject: [PATCH] initial work on daemon --- configure.ac | 4 +- yasnd.c | 184 +++++++++++++++++++++++++++++++++++++-------------- 2 files changed, 137 insertions(+), 51 deletions(-) diff --git a/configure.ac b/configure.ac index e366717..bf4e9b9 100644 --- a/configure.ac +++ b/configure.ac @@ -6,13 +6,13 @@ AC_LANG([C]) AM_INIT_AUTOMAKE # Checks for programs. -AC_PROG_CC +AC_PROG_CC_C99 # Checks for libraries. PKG_CHECK_MODULES([gammu], [gammu >= 1.0]) # Checks for header files. -AC_CHECK_HEADERS([fcntl.h stdlib.h string.h syslog.h unistd.h]) +AC_CHECK_HEADERS([fcntl.h signal.h stdlib.h string.h syslog.h unistd.h]) # Checks for typedefs, structures, and compiler characteristics. diff --git a/yasnd.c b/yasnd.c index 2ffe92a..aff8f8a 100644 --- a/yasnd.c +++ b/yasnd.c @@ -1,63 +1,149 @@ -// #include - #include #include +#include #include #include #include #include #include #include +#include #include +// #include + +// Target hosts count +#define NUM_HOSTS 3 + +// Should we do excessive debug logging or not +#define DEBUG + +typedef struct { + char* hostname; // address of host + pid_t helper_pid; // pid of helper('pinger') child process + int fail_count; // how many times in a row host was unreachable +} host_decl; + +host_decl hosts[NUM_HOSTS]; + +void init() +{ + hosts[0].hostname="10.0.0.1"; + hosts[0].fail_count=0; + hosts[1].hostname="10.0.0.2"; + hosts[1].fail_count=0; + hosts[2].hostname="10.0.0.254"; + hosts[2].fail_count=0; +} + +void log_event(const char *message) +{ + #ifdef DEBUG + syslog(LOG_INFO,"%s",message); + #endif +} + +void check_host(int num,host_decl host) +{ + pid_t pid = fork(); + if (pid < 0) { + exit(EXIT_FAILURE); + } + // If pid == 0, then we are in the child + if (pid == 0) { + char tmp[50]; + sprintf(tmp, "Pinging host %s", host.hostname); + log_event(tmp); + execl("/bin/ping","/bin/ping","-c 4","-n",host.hostname,(char*) 0); + // STUB: check result of exec call + exit(EXIT_SUCCESS); + } + // Save child's pid + host.helper_pid=pid; +} + +void loop_function() +{ + for (int i=0;i 0) + { + if (WIFEXITED(pid_status)) + { + char tmp[50]; + sprintf(tmp, "Finished child %d with result %d", result, WEXITSTATUS(pid_status)); + log_event(tmp); + // if host is alive - reset failure counter + // otherwise - increment it + if (WEXITSTATUS(pid_status) == 0) + hosts[i].fail_count=0; + else + hosts[i].fail_count++; + } + } + } +} + +void termination_handler(int signum) +{ + closelog(); + exit(EXIT_SUCCESS); +} int main(void) { - - /* Our process ID and Session ID */ - pid_t pid, sid; - - /* Fork off the parent process */ - pid = fork(); - if (pid < 0) { - exit(EXIT_FAILURE); - } - /* If we got a good PID, then - we can exit the parent process. */ - if (pid > 0) { - exit(EXIT_SUCCESS); - } + /* Our process ID and Session ID */ + pid_t pid, sid; - /* Change the file mode mask */ - umask(0); - - /* Open any logs here */ - - /* Create a new SID for the child process */ - sid = setsid(); - if (sid < 0) { - /* Log the failure */ - exit(EXIT_FAILURE); - } - + /* Fork off the parent process */ + pid = fork(); + if (pid < 0) { + exit(EXIT_FAILURE); + } + /* If we got a good PID, then we can exit the parent process. */ + if (pid > 0) { + exit(EXIT_SUCCESS); + } - - /* Change the current working directory */ - if ((chdir("/")) < 0) { - /* Log the failure */ - exit(EXIT_FAILURE); - } - - /* Close out the standard file descriptors */ - close(STDIN_FILENO); - close(STDOUT_FILENO); - close(STDERR_FILENO); - - /* Daemon-specific initialization goes here */ - - /* The Big Loop */ - while (1) { - /* Do some task here ... */ - - sleep(30); /* wait 30 seconds */ - } - exit(EXIT_SUCCESS); + /* Change the file mode mask */ + umask(0); + + /* Open any logs here */ + openlog("yasnd", LOG_PID|LOG_CONS, LOG_USER); + + /* Create a new SID for the child process */ + sid = setsid(); + if (sid < 0) { + /* Log the failure */ + exit(EXIT_FAILURE); + } + + /* Change the current working directory */ + if ((chdir("/")) < 0) { + /* Log the failure */ + exit(EXIT_FAILURE); + } + + /* Close out the standard file descriptors */ + close(STDIN_FILENO); + close(STDOUT_FILENO); + close(STDERR_FILENO); + + // Set signal handler for SIGTERM + signal(SIGTERM, termination_handler); + + // Init apropriate structures + init(); + + /* The Big Loop */ + while (1) { + loop_function(); +// sleep(60); /* wait 60 seconds */ + exit(EXIT_SUCCESS); + } + exit(EXIT_SUCCESS); }