#!/usr/bin/env php = 2) { print 'The Cacti Daemon is still running' . PHP_EOL; return; } } else { fclose(STDERR); $STDERR = fopen('null', 'wb'); } print 'Starting Cacti Daemon ... '; if (!$foreground) { if (function_exists('pcntl_fork')) { // Close the database connection db_close(); // Fork the current process to daemonize $pid = pcntl_fork(); if ($pid == -1) { // Something went wrong print '[FAILED]' . PHP_EOL; exit(1); } if ($pid == 0) { // We are the child } else { cacti_log('NOTE: Cacti Daemon PID[' . getmypid() . '] Started on Device[' . gethostname() . ']'); admin_email(__('Cacti System Notice'), __('Notice: Cacti Daemon PID[' . getmypid() . '] Started on Device[' . gethostname() . ']', true, 'CACTID')); print '[OK]' . PHP_EOL; exit(0); } } else { // On Windows we run in foreground mode print '[OK]' . PHP_EOL . '[NOTE] This system does not support forking.' . PHP_EOL; } } else { print '[OK]' . PHP_EOL . '[NOTE] The Cacti Daemon is running in foreground mode.' . PHP_EOL; } sleep(2); while (true) { wait_for_start($frequency); $reconnect_conn = false; db_check_reconnect($reconnect_conn, $logrecon); run_poller(); // Force Cacti to check the service start frequency dynamically $frequency = -1; $logrecon = true; } /** * sig_handler - provides a generic means to catch exceptions to the Cacti log. * * @param int $signo The signal that was thrown by the interface. * * @return void */ function sig_handler(int $signo) : void { global $hostname; switch ($signo) { case SIGTERM: case SIGINT: cacti_log('WARNING: Cacti Daemon PID[' . getmypid() . '] Terminated on Device[' . gethostname() . ']', true, 'CACTID'); admin_email(__('Cacti System Warning'), __('WARNING: Cacti Daemon PID[' . getmypid() . '] Terminated on Device[' . gethostname() . ']', true, 'CACTID')); exit(1); default: // ignore all other signals } } /** * wait_for_start * * @param int $frequency * * @return int */ function wait_for_start(int $frequency = -1) : int { $prev_time = -1; $i = 0; while (true) { if ($frequency <= 0) { $frequency = read_config_option('cron_interval', true); if (empty($frequency)) { $frequency = 300; } } $now = time(); $offset = $now % $frequency; if ($i % 5 == 0) { debug('PrevOS: ' . $prev_time . ', CurrOS: ' . $offset . ', Freq: ' . $frequency); } if ($prev_time > 0) { if ($offset < $prev_time) { debug('Time to Run Poller'); break; } } $prev_time = $offset; $i++; sleep(1); } return $frequency; } /** * run_poller * * @return void */ function run_poller() : void { global $debug; debug('Cacti Data Collector'); $php_binary = poller_php_binary(read_config_option('path_php_binary')); $command = poller_cactid_arguments(CACTI_PATH_BASE, $debug); debug('Command Line is: ' . implode(' ', array_merge([$php_binary], $command))); poller_enable_child_reaping(); exec_background_process($php_binary, $command); } /** * get_options * * @return array */ function get_options() : array { $parms = $_SERVER['argv']; array_shift($parms); $options = []; if (sizeof($parms)) { $shortopts = 'VvHh'; $longopts = [ 'foreground', 'debug', 'version', 'help' ]; $options = getopt($shortopts, $longopts); foreach ($options as $arg => $value) { switch($arg) { case 'foreground': case 'debug': break; case 'version': case 'V': case 'v': display_version(); exit(0); case 'help': case 'H': case 'h': display_help(); exit(0); default: print "ERROR: Invalid Argument: ($arg)" . PHP_EOL . PHP_EOL; display_help(); exit(1); } } } return $options; } /** * debug * * @param string $string * * @return void */ function debug(string $string) : void { global $debug; if ($debug) { $output = 'DEBUG: ' . trim($string); print $output . PHP_EOL; } } /** * display_version * * @return void */ function display_version() : void { $version = get_cacti_cli_version(); print 'The Cacti Daemon (cactid), Version ' . $version . ', ' . COPYRIGHT_YEARS . PHP_EOL; } /** * display_help - displays the usage of the function * * @return void */ function display_help() : void { display_version(); print PHP_EOL . 'usage: cactid.php [ --foreground ] [ --debug ]' . PHP_EOL . PHP_EOL; print 'Daemon for Cacti data collection, otherwise known as cactid.' . PHP_EOL; print 'optional:' . PHP_EOL; print ' --foreground Run cactid in foreground mode, otherwise this is a forking daemon.' . PHP_EOL; print ' --debug Used for debugging in --foreground mode.' . PHP_EOL; }