Skip to content
Snippets Groups Projects
Commit 2570bdb7 authored by Eric Vidal's avatar Eric Vidal :speech_balloon:
Browse files

consider module/bundle as a box.

Module and bundle should only know about services inside its.
Spawn a new process with its own graph when dealing with module/bundle services.
parent 94ac4ed1
No related branches found
No related tags found
No related merge requests found
......@@ -19,10 +19,44 @@
#include <66/ssexec.h>
#include <66/graph.h>
#include <skalibs/tai.h>
#include <66/service.h>
#define DATASIZE 63
#define SVC_FLAGS_STARTING 1 // 1 starting not really up
#define SVC_FLAGS_STOPPING (1 << 1) // 2 stopping not really down
#define SVC_FLAGS_UP (1 << 2) // 4 really up
#define SVC_FLAGS_DOWN (1 << 3) // 8 really down
#define SVC_FLAGS_BLOCK (1 << 4) // 16 all deps are not up/down
#define SVC_FLAGS_UNBLOCK (1 << 5) // 32 all deps are up/down
#define SVC_FLAGS_FATAL (1 << 6) // 64 process crashed
typedef struct pidservice_s pidservice_t, *pidservice_t_ref ;
struct pidservice_s
{
int pipe[2] ;
pid_t pid ;
int aresid ; // id at array ares
unsigned int vertex ; // id at graph_hash_t struct
uint8_t state ;
int nedge ;
unsigned int edge[SS_MAX_SERVICE + 1] ; // array of id at graph_hash_t struct
int nnotif ;
/** id at graph_hash_t struct of depends/requiredby service
* to notify when a service is started/stopped */
unsigned int notif[SS_MAX_SERVICE + 1] ;
} ;
#define PIDSERVICE_ZERO { { -1, -1 }, -1, -1, 0, 0, 0, { 0 } }
extern int svc_launch(pidservice_t *apids, unsigned int len, uint8_t what, graph_t *graph, resolve_service_t *ares, uint8_t timeout, ssexec_t *info, char const *rise, uint8_t rise_opt, uint8_t msg, char const *signal, uint8_t propagate) ;
extern int svc_compute_ns(resolve_service_t *res, uint8_t what, uint8_t timeout, ssexec_t *info, char const *updown, uint8_t opt_updown, uint8_t reloadmsg,char const *data, uint8_t propagate) ;
extern int svc_scandir_ok (char const *dir) ;
extern int svc_scandir_send(char const *scandir,char const *signal) ;
extern int svc_send(char const *const *list, unsigned int nservice, char **sig, unsigned int siglen, ssexec_t *info) ;
extern int svc_send_wait(char const *const *list, unsigned int nservice, char **sig, unsigned int siglen, ssexec_t *info) ;
extern void svc_unsupervise(unsigned int *alist, unsigned int alen, graph_t *g, resolve_service_t *ares, unsigned int areslen) ;
extern void svc_send_fdholder(char const *socket) ;
#endif
This diff is collapsed.
svc_compute_ns.o
svc_launch.o
svc_scandir_ok.o
svc_scandir_send.o
svc_send.o
svc_send_fdholder.o
svc_send_wait.o
svc_unsupervise.o
-ls6
......
/*
* ssexec_compute_ns.c
*
* Copyright (c) 2018-2021 Eric Vidal <eric@obarun.org>
*
* All rights reserved.
*
* This file is part of Obarun. It is subject to the license terms in
* the LICENSE file found in the top-level directory of this
* distribution.
* This file may not be copied, modified, propagated, or distributed
* except according to the terms contained in the LICENSE file./
*/
#include <stdint.h>
#include <oblibs/log.h>
#include <oblibs/graph.h>
#include <oblibs/types.h>
#include <oblibs/sastr.h>
#include <skalibs/genalloc.h>
#include <66/svc.h>
#include <66/config.h>
#include <66/resolve.h>
#include <66/ssexec.h>
#include <66/state.h>
#include <66/enum.h>
#include <66/service.h>
#include <66/sanitize.h>
#include <s6/supervise.h>//s6_svstatus_t
static pidservice_t pidservice_init(unsigned int len)
{
log_flow() ;
pidservice_t pids = PIDSERVICE_ZERO ;
if (len > SS_MAX_SERVICE)
log_die(LOG_EXIT_SYS, "too many services") ;
graph_array_init_single(pids.edge, len) ;
return pids ;
}
static void pidservice_init_array(unsigned int *list, unsigned int listlen, pidservice_t *apids, graph_t *g, resolve_service_t *ares, unsigned int areslen, ssexec_t *info, uint8_t requiredby, uint32_t flag) {
log_flow() ;
int r = 0 ;
unsigned int pos = 0 ;
for (; pos < listlen ; pos++) {
pidservice_t pids = pidservice_init(g->mlen) ;
char *name = g->data.s + genalloc_s(graph_hash_t,&g->hash)[list[pos]].vertex ;
pids.aresid = service_resolve_array_search(ares, areslen, name) ;
if (pids.aresid < 0)
log_dieu(LOG_EXIT_SYS,"find ares id of: ", name, " -- please make a bug reports") ;
if (FLAGS_ISSET(flag, STATE_FLAGS_TOPROPAGATE)) {
pids.nedge = graph_matrix_get_edge_g_sorted_list(pids.edge, g, name, requiredby, 1) ;
if (pids.nedge < 0)
log_dieu(LOG_EXIT_SYS,"get sorted ", requiredby ? "required by" : "dependency", " list of service: ", name) ;
pids.nnotif = graph_matrix_get_edge_g_sorted_list(pids.notif, g, name, !requiredby, 1) ;
if (pids.nnotif < 0)
log_dieu(LOG_EXIT_SYS,"get sorted ", !requiredby ? "required by" : "dependency", " list of service: ", name) ;
}
pids.vertex = graph_hash_vertex_get_id(g, name) ;
if (pids.vertex < 0)
log_dieu(LOG_EXIT_SYS, "get vertex id -- please make a bug report") ;
if (ares[pids.aresid].type != TYPE_CLASSIC) {
ss_state_t ste = STATE_ZERO ;
if (!state_read(&ste, &ares[pids.aresid]))
log_dieusys(LOG_EXIT_SYS, "read state file of: ", name) ;
if (ste.isup == STATE_FLAGS_TRUE)
FLAGS_SET(pids.state, SVC_FLAGS_UP) ;
else
FLAGS_SET(pids.state, SVC_FLAGS_DOWN) ;
} else {
s6_svstatus_t status ;
r = s6_svstatus_read(ares[pids.aresid].sa.s + ares[pids.aresid].live.scandir, &status) ;
pid_t pid = !r ? 0 : status.pid ;
if (pid > 0) {
FLAGS_SET(pids.state, SVC_FLAGS_UP) ;
}
else
FLAGS_SET(pids.state, SVC_FLAGS_DOWN) ;
}
apids[pos] = pids ;
}
}
int svc_compute_ns(resolve_service_t *res, uint8_t what, uint8_t timeout, ssexec_t *info, char const *updown, uint8_t opt_updown, uint8_t reloadmsg,char const *data, uint8_t propagate)
{
log_flow() ;
int r ;
uint8_t requiredby = 0 ;
size_t pos = 0 ;
graph_t graph = GRAPH_ZERO ;
stralloc sa = STRALLOC_ZERO ;
unsigned int napid = 0 ;
unsigned int areslen = 0, list[SS_MAX_SERVICE], visit[SS_MAX_SERVICE] ;
resolve_service_t ares[SS_MAX_SERVICE] ;
uint32_t gflag = STATE_FLAGS_TOPROPAGATE|STATE_FLAGS_WANTUP ;
if (!propagate)
FLAGS_CLEAR(gflag, STATE_FLAGS_TOPROPAGATE) ;
if (what) {
requiredby = 1 ;
FLAGS_SET(gflag, STATE_FLAGS_WANTDOWN) ;
FLAGS_CLEAR(gflag, STATE_FLAGS_WANTUP) ;
}
if (res->dependencies.ncontents) {
if (!sastr_clean_string(&sa, res->sa.s + res->dependencies.contents))
log_dieu(LOG_EXIT_SYS, "clean string") ;
} else {
log_warn("empty ns: ", res->sa.s + res->name) ;
return 0 ;
}
/** build the graph of the ns */
service_graph_g(sa.s, sa.len, &graph, ares, &areslen, info, gflag) ;
if (!graph.mlen)
log_die(LOG_EXIT_USER, "services selection is not supervised -- initiate its first") ;
graph_array_init_single(visit, SS_MAX_SERVICE) ;
FOREACH_SASTR(&sa, pos) {
char const *name = sa.s + pos ;
int aresid = service_resolve_array_search(ares, areslen, name) ;
if (aresid < 0)
log_die(LOG_EXIT_USER, "service: ", name, " not available -- did you parsed it?") ;
graph_compute_visit(name, visit, list, &graph, &napid, requiredby) ;
}
if (!what)
sanitize_init(list, napid, &graph, ares, areslen, STATE_FLAGS_UNKNOWN) ;
pidservice_t apids[napid] ;
pidservice_init_array(list, napid, apids, &graph, ares, areslen, info, requiredby, gflag) ;
r = svc_launch(apids, napid, what, &graph, ares, info->timeout ? info->timeout : 0, info, updown, opt_updown, reloadmsg, data, propagate) ;
graph_free_all(&graph) ;
service_resolve_array_free(ares, areslen) ;
stralloc_free(&sa) ;
return r ;
}
This diff is collapsed.
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