[luad] add an Erlang-style supervisior to the daemon
This commit is contained in:
parent
36746544ee
commit
7e99548842
|
@ -36,6 +36,9 @@
|
||||||
|
|
||||||
#define DAEMON_VARRUN "/var/run"
|
#define DAEMON_VARRUN "/var/run"
|
||||||
|
|
||||||
|
#define SUP_ALLOWED_RESTARTS 10
|
||||||
|
#define SUP_MAX_SECONDS 60
|
||||||
|
|
||||||
#include <pwd.h>
|
#include <pwd.h>
|
||||||
#include <grp.h>
|
#include <grp.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
@ -44,6 +47,7 @@
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
#include <time.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <sys/time.h>
|
#include <sys/time.h>
|
||||||
#include <sys/unistd.h>
|
#include <sys/unistd.h>
|
||||||
|
@ -64,6 +68,42 @@
|
||||||
#include <lua5.1/lauxlib.h>
|
#include <lua5.1/lauxlib.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
struct restart_s {
|
||||||
|
int i;
|
||||||
|
time_t time[SUP_ALLOWED_RESTARTS];
|
||||||
|
};
|
||||||
|
|
||||||
|
static void restart_init(struct restart_s *restart) {
|
||||||
|
restart->i = 0;
|
||||||
|
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < SUP_ALLOWED_RESTARTS; i++) {
|
||||||
|
restart->time[i] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void restart_add(struct restart_s *restart, time_t new_restart) {
|
||||||
|
restart->time[restart->i++] = new_restart;
|
||||||
|
restart->i %= SUP_ALLOWED_RESTARTS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int restart_max(struct restart_s *restart) {
|
||||||
|
int i, total;
|
||||||
|
|
||||||
|
for (i = 0; i < SUP_ALLOWED_RESTARTS; i++) {
|
||||||
|
if (restart->time[i] > time(NULL) - SUP_MAX_SECONDS) {
|
||||||
|
total++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (total == SUP_ALLOWED_RESTARTS) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void sigterm(int signo)
|
static void sigterm(int signo)
|
||||||
{
|
{
|
||||||
daemon_log(LOG_INFO, "Caught a SIGTERM. Exiting... ");
|
daemon_log(LOG_INFO, "Caught a SIGTERM. Exiting... ");
|
||||||
|
@ -292,19 +332,34 @@ int main(int argc, char *argv[])
|
||||||
daemon_retval_send(0);
|
daemon_retval_send(0);
|
||||||
daemon_log(LOG_INFO, "Sucessfully started with DEAMON=%s and DAEMON_PATH=%s", daemon_log_ident, runtime_path);
|
daemon_log(LOG_INFO, "Sucessfully started with DEAMON=%s and DAEMON_PATH=%s", daemon_log_ident, runtime_path);
|
||||||
|
|
||||||
/* Create a new Lua environment */
|
|
||||||
L = luaL_newstate();
|
|
||||||
/* And load the standard libraries into the Lua environment */
|
|
||||||
luaL_openlibs(L);
|
|
||||||
/* Derive the Lua daemon path from the C daemon one */
|
/* Derive the Lua daemon path from the C daemon one */
|
||||||
asprintf(&luad_path, "%s%s", (const char *)argv[0], ".lua");
|
asprintf(&luad_path, "%s%s", (const char *)argv[0], ".lua");
|
||||||
/* Tunnel through the wormhole into Lua neverland. This call should never return. */
|
|
||||||
if (luaL_dofile(L, (const char *)luad_path)) {
|
|
||||||
daemon_log(LOG_ERR, "Lua returned with error message: %s", lua_tostring(L,-1));
|
|
||||||
}
|
|
||||||
/* Clean up the Lua state */
|
|
||||||
lua_close(L);
|
|
||||||
|
|
||||||
|
/* Erlang-style supervisor */
|
||||||
|
struct restart_s restart;
|
||||||
|
restart_init(&restart);
|
||||||
|
|
||||||
|
while(1) {
|
||||||
|
/* Stop when allowed number of restarts have occurred in specified time window */
|
||||||
|
if (restart_max(&restart)) {
|
||||||
|
daemon_log(LOG_ERR, "%d restarts within a %d sec window", SUP_ALLOWED_RESTARTS, SUP_MAX_SECONDS);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Create a new Lua environment */
|
||||||
|
L = luaL_newstate();
|
||||||
|
/* And load the standard libraries into the Lua environment */
|
||||||
|
luaL_openlibs(L);
|
||||||
|
/* Tunnel through the wormhole into Lua neverland. This call should never return. */
|
||||||
|
if (luaL_dofile(L, (const char *)luad_path)) {
|
||||||
|
daemon_log(LOG_ERR, "%s", lua_tostring(L,-1));
|
||||||
|
}
|
||||||
|
/* Clean up the Lua state */
|
||||||
|
lua_close(L);
|
||||||
|
/* Wait for one second before restarting the Lua daemon */
|
||||||
|
sleep(1);
|
||||||
|
restart_add(&restart, time(NULL));
|
||||||
|
}
|
||||||
|
|
||||||
/* Do a cleanup */
|
/* Do a cleanup */
|
||||||
finish:
|
finish:
|
||||||
|
|
Loading…
Reference in New Issue