fiss

Friedel's Initialization and Service Supervision
Log | Files | Refs | LICENSE

commit 8be66b2a0d7df39d851422638fab95c9aa852aeb
parent 9c7d7b4f0d6f3b742d65f50c65e2112a9ee7deb1
Author: Friedel Schön <[email protected]>
Date:   Mon,  5 Jun 2023 14:01:37 +0200

implementing service_update_state instead of service_update_status

Diffstat:
Minclude/service.h | 2+-
Msrc/handle_command.c | 7+------
Msrc/handle_exit.c | 21++++++++-------------
Msrc/register.c | 3+--
Msrc/start.c | 19++++++++-----------
Msrc/status.c | 25++++++++++++++++++++++++-
Msrc/stop.c | 23++++++-----------------
Msrc/supervise.c | 25-------------------------
8 files changed, 49 insertions(+), 76 deletions(-)

diff --git a/include/service.h b/include/service.h @@ -116,5 +116,5 @@ const char* service_status_name(service_t* s); void service_stop(service_t* s); int service_supervise(const char* service_dir, const char* runlevel); void service_update_dependency(service_t* s); -void service_update_status(service_t* s); bool service_is_dependency(service_t* s); +void service_update_state(service_t* s, int state); diff --git a/src/handle_command.c b/src/handle_command.c @@ -98,16 +98,11 @@ void service_handle_command(service_t* s, service_command_t command, char data) s->fail_count = 0; if (s->state == STATE_DEAD) - s->state = STATE_INACTIVE; + service_update_state(s, STATE_INACTIVE); - s->status_change = time(NULL); - service_update_status(s); break; case X_EXIT: // ignored return; } - - s->status_change = time(NULL); - service_update_status(s); } diff --git a/src/handle_exit.c b/src/handle_exit.c @@ -14,20 +14,18 @@ static void do_finish(service_t* s) { struct stat st; if (fstatat(s->dir, "finish", &st, 0) != -1 && st.st_mode & S_IXUSR) { - s->state = STATE_FINISHING; if ((s->pid = fork_dup_cd_exec(s->dir, "./finish", null_fd, null_fd, null_fd)) == -1) { print_error("error: cannot execute ./finish: %s\n"); - s->state = STATE_INACTIVE; + service_update_state(s, STATE_INACTIVE); + } else { + service_update_state(s, STATE_FINISHING); } } else if (s->fail_count == SV_FAIL_MAX) { - s->state = STATE_DEAD; + service_update_state(s, STATE_DEAD); printf("%s died\n", s->name); } else { - s->state = STATE_INACTIVE; + service_update_state(s, STATE_INACTIVE); } - - s->status_change = time(NULL); - service_update_status(s); } @@ -73,16 +71,16 @@ void service_handle_exit(service_t* s, bool signaled, int return_code) { case STATE_FINISHING: if (s->fail_count == SV_FAIL_MAX) { - s->state = STATE_DEAD; + service_update_state(s, STATE_DEAD); printf("%s died\n", s->name); } else { - s->state = STATE_INACTIVE; + service_update_state(s, STATE_INACTIVE); } break; case STATE_STARTING: if (!signaled && return_code == 0) { if (fstatat(s->dir, "stop", &st, 0) != -1 && st.st_mode & S_IXUSR) { - s->state = STATE_ACTIVE_BACKGROUND; + service_update_state(s, STATE_ACTIVE_BACKGROUND); } else { do_finish(s); } @@ -103,7 +101,4 @@ void service_handle_exit(service_t* s, bool signaled, int return_code) { case STATE_INACTIVE: printf("warn: %s died but was set to inactive\n", s->name); } - - s->status_change = time(NULL); - service_update_status(s); } diff --git a/src/register.c b/src/register.c @@ -113,8 +113,7 @@ service_t* service_register(int dir, const char* name, bool is_log_service) { strncpy(s->name, name, sizeof(s->name)); - s->status_change = time(NULL); - service_update_status(s); + service_update_state(s, -1); } if (s->is_log_service) { diff --git a/src/start.c b/src/start.c @@ -86,14 +86,14 @@ void service_run(service_t* s) { struct stat st; if (fstatat(s->dir, "run", &st, 0) != -1 && st.st_mode & S_IXUSR) { - s->state = STATE_ACTIVE_FOREGROUND; + service_update_state(s, STATE_ACTIVE_FOREGROUND); } else if (fstatat(s->dir, "start", &st, 0) != -1 && st.st_mode & S_IXUSR) { - s->state = STATE_STARTING; + service_update_state(s, STATE_STARTING); } else if (fstatat(s->dir, "depends", &st, 0) != -1 && st.st_mode & S_IREAD) { - s->state = STATE_ACTIVE_DUMMY; + service_update_state(s, STATE_ACTIVE_DUMMY); } else { - fprintf(stderr, "warn: %s: `run`, `start` or `depends` not found\n", s->name); - s->state = STATE_INACTIVE; + // fprintf(stderr, "warn: %s: `run`, `start` or `depends` not found\n", s->name); + service_update_state(s, STATE_INACTIVE); } if (s->state != STATE_ACTIVE_DUMMY) { @@ -131,8 +131,6 @@ void service_run(service_t* s) { _exit(1); } } - s->status_change = time(NULL); - service_update_status(s); } void service_start(service_t* s) { @@ -148,13 +146,12 @@ void service_start(service_t* s) { } if (fstatat(s->dir, "setup", &st, 0) != -1 && st.st_mode & S_IXUSR) { - s->state = STATE_SETUP; if ((s->pid = fork_dup_cd_exec(s->dir, "./setup", null_fd, null_fd, null_fd)) == -1) { print_error("error: cannot execute ./setup: %s\n"); - s->state = STATE_INACTIVE; + service_update_state(s, STATE_INACTIVE); + } else { + service_update_state(s, STATE_SETUP); } - s->status_change = time(NULL); - service_update_status(s); } else { service_run(s); } diff --git a/src/status.c b/src/status.c @@ -11,7 +11,7 @@ #include <unistd.h> -void service_update_status(service_t* s) { +static void service_update_status(service_t* s) { int fd; const char* stat_human; service_serial_t stat_runit; @@ -56,3 +56,26 @@ void service_update_status(service_t* s) { renameat(s->dir, "supervise/stat.new", s->dir, "supervise/stat"); renameat(s->dir, "supervise/pid.new", s->dir, "supervise/pid"); } + +void service_update_state(service_t* s, int state) { + if (state != -1) + s->state = state; + + s->status_change = time(NULL); + service_update_status(s); + + for (int i = 0; i < services_size; i++) { + s = &services[i]; + if (s->state == STATE_DEAD) + continue; + if (service_need_restart(s)) { + if (s->state == STATE_INACTIVE) { + service_start(s); + } + } else { + if (s->state != STATE_INACTIVE) { + service_stop(s); + } + } + } +} diff --git a/src/stop.c b/src/stop.c @@ -13,34 +13,23 @@ void service_stop(service_t* s) { switch (s->state) { case STATE_ACTIVE_DUMMY: service_handle_exit(s, false, 0); - - s->status_change = time(NULL); - service_update_status(s); - break; - case STATE_ACTIVE_FOREGROUND: - case STATE_SETUP: - kill(s->pid, SIGTERM); - - s->status_change = time(NULL); - service_update_status(s); break; case STATE_ACTIVE_BACKGROUND: - s->state = STATE_STOPPING; if ((s->pid = fork_dup_cd_exec(s->dir, "./stop", null_fd, null_fd, null_fd)) == -1) { print_error("error: cannot execute ./stop: %s\n"); - s->state = STATE_INACTIVE; + service_update_state(s, STATE_INACTIVE); + } else { + service_update_state(s, STATE_STOPPING); } - - s->status_change = time(NULL); - service_update_status(s); break; + case STATE_ACTIVE_FOREGROUND: + case STATE_SETUP: case STATE_STARTING: case STATE_STOPPING: case STATE_FINISHING: kill(s->pid, SIGTERM); - s->status_change = time(NULL); - service_update_status(s); + service_update_state(s, -1); break; case STATE_INACTIVE: case STATE_DEAD: diff --git a/src/supervise.c b/src/supervise.c @@ -44,30 +44,6 @@ static void signal_child(int unused) { service_handle_exit(s, WIFSIGNALED(status), WIFSIGNALED(status) ? WTERMSIG(status) : WEXITSTATUS(status)); } -static void check_services(void) { - service_t* s; - - for (int i = 0; i < services_size; i++) { - s = &services[i]; - if (s->state == STATE_DEAD) - continue; - if (service_need_restart(s)) { - if (s->state == STATE_INACTIVE) { - service_start(s); - s->status_change = time(NULL); - service_update_status(s); - } - } else { - if (s->state != STATE_INACTIVE) { - service_stop(s); - s->status_change = time(NULL); - service_update_status(s); - } - } - } -} - - static void control_sockets(void) { service_t* s; char cmd, chr; @@ -118,7 +94,6 @@ int service_supervise(const char* service_dir_, const char* runlevel_) { // accept connections and handle requests while (daemon_running) { service_refresh_directory(); - check_services(); control_sockets(); sleep(SV_CHECK_INTERVAL); }