Skip to content
Snippets Groups Projects
Commit 6476a41f authored by g0dil's avatar g0dil
Browse files

Utils/Daemon: Add instance() and logReopen() member and bind SIGHUP to logReopen()

parent e01ba6d7
No related branches found
No related tags found
No related merge requests found
......@@ -123,6 +123,35 @@ prefix_ void senf::Daemon::openLog()
}
}
prefix_ void senf::Daemon::logReopen()
{
if (! stdoutLog_.empty()) {
int fd (::open(stdoutLog_.c_str(), O_WRONLY | O_APPEND | O_CREAT, 0666));
if (fd < 0)
goto error;
if (::dup2(fd, 1) < 0)
goto error;
if (stderrLog_ == stdoutLog_) {
if (::dup2(fd, 2) < 0)
goto error;
return;
}
}
if (! stderrLog_.empty()) {
int fd (::open(stderrLog_.c_str(), O_WRONLY | O_APPEND | O_CREAT, 0666));
if (fd < 0)
goto error;
if (::dup2(fd, 2) < 0)
goto error;
}
return;
error:
SENF_LOG(
(senf::log::CRITICAL)
("log-file reopen failed: (" << errno << ") " << ::strerror(errno)) );
}
prefix_ void senf::Daemon::pidFile(std::string const & f)
{
pidfile_ = f;
......@@ -234,13 +263,24 @@ prefix_ int senf::Daemon::start(int argc, char ** argv)
return 0;
}
prefix_ senf::Daemon & senf::Daemon::instance()
{
BOOST_ASSERT( instance_ );
return *instance_;
}
////////////////////////////////////////
// protected members
prefix_ senf::Daemon::Daemon()
: argc_(0), argv_(0), daemonize_(true), stdout_(-1), stderr_(-1), pidfile_(""),
pidfileCreated_(false), detached_(false)
{}
{
BOOST_ASSERT( ! instance_ );
instance_ = this;
}
senf::Daemon * senf::Daemon::instance_ (0);
////////////////////////////////////////
// private members
......@@ -466,12 +506,25 @@ namespace {
#endif
namespace {
void sighupHandler(int sig)
{
senf::Daemon::instance().logReopen();
}
}
prefix_ void senf::Daemon::installSighandlers()
{
#ifdef SENF_DEBUG
struct ::sigaction sa;
sa.sa_sigaction = &fatalSignalsHandler;
::sigemptyset(&sa.sa_mask);
sa.sa_handler = &sighupHandler;
sa.sa_flags = SA_RESTART;
::sigaction(SIGHUP, &sa, NULL);
#ifdef SENF_DEBUG
sa.sa_sigaction = &fatalSignalsHandler;
sa.sa_flags = SA_RESTART | SA_SIGINFO;
::sigaction(SIGILL, &sa, NULL);
......
......@@ -28,6 +28,7 @@
// Custom includes
#include <boost/utility.hpp>
#include "../Logger/SenfLog.hh"
//#include "Daemon.mpp"
///////////////////////////////hh.p////////////////////////////////////////
......@@ -103,6 +104,8 @@ namespace senf {
class Daemon : boost::noncopyable
{
public:
SENF_LOG_CLASS_AREA();
///////////////////////////////////////////////////////////////////////////
// Types
......@@ -158,12 +161,18 @@ namespace senf {
static void exit(unsigned code=0); ///< Terminate daemon with failure
void logReopen(); ///< Reopen the log files
/**< This is used when rotating the logs. By default,
SIGHUP calls logReopen. */
///\}
int start(int argc, char ** argv); ///< Called from main() to launch daemon.
/**< Normally not called directly but from the
\ref SENF_DAEMON_MAIN macro. */
static Daemon & instance(); ///< Return the Daemon instance
protected:
Daemon();
......@@ -212,6 +221,8 @@ namespace senf {
bool pidfileCreated_;
bool detached_;
static Daemon * instance_;
};
/** \brief Provide \c main() function
......
......@@ -77,9 +77,11 @@ namespace {
return instance.start(argc, argv);
}
int pid;
int run(int argc, char ** argv)
{
int pid (::fork());
pid = ::fork();
if (pid < 0) throw senf::SystemException("::fork()");
if (pid == 0) {
::_exit(myMain(argc, argv));
......@@ -100,16 +102,29 @@ BOOST_AUTO_UNIT_TEST(testDaemon)
BOOST_CHECK( ! boost::filesystem::exists("invalid.log") );
BOOST_CHECK( ! boost::filesystem::exists("invalid.pid") );
BOOST_CHECK( boost::filesystem::exists("testDaemon.pid") );
BOOST_REQUIRE( boost::filesystem::exists("testDaemon.pid") );
BOOST_REQUIRE( boost::filesystem::exists("testDaemon.log") );
boost::filesystem::rename("testDaemon.log", "testDaemon.log.1");
{
std::ifstream pidFile ("testDaemon.pid");
int pid (0);
BOOST_REQUIRE( pidFile >> pid );
BOOST_REQUIRE( pid != 0 );
::kill(pid, SIGHUP);
}
delay(1000);
BOOST_CHECK( ! boost::filesystem::exists("testDaemon.pid") );
BOOST_REQUIRE( boost::filesystem::exists("testDaemon.log") );
BOOST_CHECK( boost::filesystem::exists("testDaemon.log") );
BOOST_REQUIRE( boost::filesystem::exists("testDaemon.log.1") );
std::ifstream log ("testDaemon.log");
std::ifstream log ("testDaemon.log.1");
std::stringstream data;
data << log.rdbuf();
BOOST_CHECK_EQUAL( data.str(), "Running init()\nRunning run()\n" );
BOOST_CHECK_NO_THROW( boost::filesystem::remove("testDaemon.log") );
BOOST_CHECK_NO_THROW( boost::filesystem::remove("testDaemon.log.1") );
}
///////////////////////////////cc.e////////////////////////////////////////
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment