herdd: rename runlevels to targets
This commit is contained in:
+11
-11
@@ -1,8 +1,8 @@
|
|||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "queue.h"
|
#include "queue.h"
|
||||||
#include "runlevel.h"
|
|
||||||
#include "service.h"
|
#include "service.h"
|
||||||
#include "spawn.h"
|
#include "spawn.h"
|
||||||
|
#include "target.h"
|
||||||
|
|
||||||
#include <dirent.h>
|
#include <dirent.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
@@ -46,7 +46,7 @@ static int load_services(const char *dir, struct queue *out)
|
|||||||
snprintf(filepath, sizeof filepath, "%s/%s", dir, dent->d_name);
|
snprintf(filepath, sizeof filepath, "%s/%s", dir, dent->d_name);
|
||||||
tracef(" - %s\n", dent->d_name);
|
tracef(" - %s\n", dent->d_name);
|
||||||
struct service *s = NULL;
|
struct service *s = NULL;
|
||||||
int err = service_load(filepath, &s);
|
int err = service_load(dent->d_name, filepath, &s);
|
||||||
if (err != SUCCESS) {
|
if (err != SUCCESS) {
|
||||||
printf("failed to load %s (%s)\n",
|
printf("failed to load %s (%s)\n",
|
||||||
filepath,
|
filepath,
|
||||||
@@ -60,7 +60,7 @@ static int load_services(const char *dir, struct queue *out)
|
|||||||
return SUCCESS;
|
return SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int load_runlevels(const char *dir, struct queue *out)
|
static int load_targets(const char *dir, struct queue *out)
|
||||||
{
|
{
|
||||||
DIR *d = opendir(dir);
|
DIR *d = opendir(dir);
|
||||||
if (!d) {
|
if (!d) {
|
||||||
@@ -74,8 +74,8 @@ static int load_runlevels(const char *dir, struct queue *out)
|
|||||||
char filepath[4096];
|
char filepath[4096];
|
||||||
snprintf(filepath, sizeof filepath, "%s/%s", dir, dent->d_name);
|
snprintf(filepath, sizeof filepath, "%s/%s", dir, dent->d_name);
|
||||||
tracef(" - %s\n", dent->d_name);
|
tracef(" - %s\n", dent->d_name);
|
||||||
struct runlevel *rl = NULL;
|
struct target *rl = NULL;
|
||||||
int err = runlevel_load(filepath, &rl);
|
int err = target_load(dent->d_name, filepath, &rl);
|
||||||
if (err != SUCCESS) {
|
if (err != SUCCESS) {
|
||||||
printf("failed to load %s (%s)\n",
|
printf("failed to load %s (%s)\n",
|
||||||
filepath,
|
filepath,
|
||||||
@@ -83,7 +83,7 @@ static int load_runlevels(const char *dir, struct queue *out)
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
tracef("runlevel: %s\n", rl->rl_description);
|
tracef("target: %s\n", rl->rl_description);
|
||||||
for (size_t i = 0; i < rl->rl_requires_count; i++) {
|
for (size_t i = 0; i < rl->rl_requires_count; i++) {
|
||||||
tracef(" requires: %s\n", rl->rl_requires[i]);
|
tracef(" requires: %s\n", rl->rl_requires[i]);
|
||||||
}
|
}
|
||||||
@@ -99,19 +99,19 @@ int main(int argc, const char *argv[], const char *envp[])
|
|||||||
{
|
{
|
||||||
sys_remote_set(SYS_REMOTE_NSD, 0, 0);
|
sys_remote_set(SYS_REMOTE_NSD, 0, 0);
|
||||||
|
|
||||||
struct queue *runlevels = global_runlevels();
|
struct queue *targets = global_targets();
|
||||||
struct queue *services = global_services();
|
struct queue *services = global_services();
|
||||||
|
|
||||||
int err = load_runlevels("/etc/herdd/runlevels", runlevels);
|
int err = load_targets("/etc/herdd/targets", targets);
|
||||||
err = load_services("/etc/herdd/services", services);
|
err = load_services("/etc/herdd/services", services);
|
||||||
|
|
||||||
struct runlevel *rl = runlevel_find("single-user");
|
struct target *rl = target_find("single-user.target");
|
||||||
if (!rl) {
|
if (!rl) {
|
||||||
log_fail("Cannot find runlevel single-user.");
|
log_fail("Cannot find target single-user.");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
runlevel_activate(rl);
|
target_activate(rl);
|
||||||
#if 1
|
#if 1
|
||||||
pid_t child = fork();
|
pid_t child = fork();
|
||||||
kern_logf(" fork returned %d", child);
|
kern_logf(" fork returned %d", child);
|
||||||
|
|||||||
@@ -1,22 +0,0 @@
|
|||||||
#ifndef RUNLEVEL_H_
|
|
||||||
#define RUNLEVEL_H_
|
|
||||||
|
|
||||||
#include "queue.h"
|
|
||||||
|
|
||||||
#include <stddef.h>
|
|
||||||
|
|
||||||
struct runlevel {
|
|
||||||
char *rl_name;
|
|
||||||
char *rl_description;
|
|
||||||
char **rl_requires;
|
|
||||||
size_t rl_requires_count;
|
|
||||||
struct queue_entry rl_entry;
|
|
||||||
};
|
|
||||||
|
|
||||||
extern struct queue *global_runlevels(void);
|
|
||||||
|
|
||||||
extern int runlevel_load(const char *path, struct runlevel **out);
|
|
||||||
extern struct runlevel *runlevel_find(const char *name);
|
|
||||||
extern int runlevel_activate(struct runlevel *rl);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
+11
-17
@@ -43,13 +43,6 @@ static int parse_service_data(fx_object *in, struct service *out)
|
|||||||
fx_hashtable *in_unit = NULL;
|
fx_hashtable *in_unit = NULL;
|
||||||
fx_value_get_object(unit_v, &in_unit);
|
fx_value_get_object(unit_v, &in_unit);
|
||||||
|
|
||||||
const fx_value *name_v = fx_hashtable_get(in_unit, &FX_CSTR("name"));
|
|
||||||
if (!name_v || !fx_value_is_type(name_v, FX_TYPE_STRING)) {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
fx_string *name = NULL;
|
|
||||||
fx_value_get_object(name_v, &name);
|
|
||||||
|
|
||||||
const fx_value *description_v
|
const fx_value *description_v
|
||||||
= fx_hashtable_get(in_unit, &FX_CSTR("description"));
|
= fx_hashtable_get(in_unit, &FX_CSTR("description"));
|
||||||
if (!description_v
|
if (!description_v
|
||||||
@@ -101,24 +94,23 @@ static int parse_service_data(fx_object *in, struct service *out)
|
|||||||
}
|
}
|
||||||
fx_iterator_unref(it);
|
fx_iterator_unref(it);
|
||||||
|
|
||||||
out->s_name = fx_string_steal(name);
|
|
||||||
out->s_description = fx_string_steal(description);
|
out->s_description = fx_string_steal(description);
|
||||||
out->s_exec = fx_string_steal(exec);
|
out->s_exec = fx_string_steal(exec);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int service_load(const char *path, struct service **out)
|
int service_load(const char *name, const char *path, struct service **out)
|
||||||
{
|
{
|
||||||
struct service *rl = malloc(sizeof *rl);
|
struct service *svc = malloc(sizeof *svc);
|
||||||
if (!rl) {
|
if (!svc) {
|
||||||
errno = ENOMEM;
|
errno = ENOMEM;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
FILE *fp = fopen(path, "r");
|
FILE *fp = fopen(path, "r");
|
||||||
if (!fp) {
|
if (!fp) {
|
||||||
free(rl);
|
free(svc);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -128,30 +120,32 @@ int service_load(const char *path, struct service **out)
|
|||||||
fx_result result = fx_serial_ctx_deserialise(ctx, in, &data, 0);
|
fx_result result = fx_serial_ctx_deserialise(ctx, in, &data, 0);
|
||||||
if (fx_result_is_error(result)) {
|
if (fx_result_is_error(result)) {
|
||||||
fx_throw(result);
|
fx_throw(result);
|
||||||
free(rl);
|
free(svc);
|
||||||
errno = EFTYPE;
|
errno = EFTYPE;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!fx_value_is_type(&data, FX_TYPE_HASHTABLE)) {
|
if (!fx_value_is_type(&data, FX_TYPE_HASHTABLE)) {
|
||||||
fx_value_unset(&data);
|
fx_value_unset(&data);
|
||||||
free(rl);
|
free(svc);
|
||||||
errno = EFTYPE;
|
errno = EFTYPE;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (parse_service_data(data.v_object, rl) != 0) {
|
if (parse_service_data(data.v_object, svc) != 0) {
|
||||||
free(rl);
|
free(svc);
|
||||||
errno = EFTYPE;
|
errno = EFTYPE;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
svc->s_name = fx_strdup(name);
|
||||||
|
|
||||||
fx_stream_unref(in);
|
fx_stream_unref(in);
|
||||||
fx_value_unset(&data);
|
fx_value_unset(&data);
|
||||||
|
|
||||||
fclose(fp);
|
fclose(fp);
|
||||||
|
|
||||||
*out = rl;
|
*out = svc;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -18,7 +18,10 @@ struct service {
|
|||||||
|
|
||||||
extern struct queue *global_services(void);
|
extern struct queue *global_services(void);
|
||||||
|
|
||||||
extern int service_load(const char *path, struct service **out);
|
extern int service_load(
|
||||||
|
const char *name,
|
||||||
|
const char *path,
|
||||||
|
struct service **out);
|
||||||
extern struct service *service_find(const char *name);
|
extern struct service *service_find(const char *name);
|
||||||
extern int service_start(struct service *svc);
|
extern int service_start(struct service *svc);
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#include "runlevel.h"
|
#include "target.h"
|
||||||
|
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "service.h"
|
#include "service.h"
|
||||||
@@ -14,36 +14,35 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
static struct queue runlevels = QUEUE_INIT;
|
static struct queue targets = QUEUE_INIT;
|
||||||
|
|
||||||
struct queue *global_runlevels(void)
|
struct queue *global_targets(void)
|
||||||
{
|
{
|
||||||
return &runlevels;
|
return &targets;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int parse_runlevel_data(fx_object *in, struct runlevel *out)
|
static int parse_target_data(fx_object *in, struct target *out)
|
||||||
{
|
{
|
||||||
if (!fx_object_is_type(in, FX_TYPE_HASHTABLE)) {
|
if (!fx_object_is_type(in, FX_TYPE_HASHTABLE)) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
const fx_value *runlevel_v = fx_hashtable_get(in, &FX_CSTR("runlevel"));
|
const fx_value *target_v = fx_hashtable_get(in, &FX_CSTR("target"));
|
||||||
if (!runlevel_v || !fx_value_is_type(runlevel_v, FX_TYPE_HASHTABLE)) {
|
if (!target_v || !fx_value_is_type(target_v, FX_TYPE_HASHTABLE)) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
fx_hashtable *in_runlevel = NULL;
|
fx_hashtable *in_target = NULL;
|
||||||
fx_value_get_object(runlevel_v, &in_runlevel);
|
fx_value_get_object(target_v, &in_target);
|
||||||
|
|
||||||
const fx_value *name_v
|
const fx_value *unit_v = fx_hashtable_get(in, &FX_CSTR("unit"));
|
||||||
= fx_hashtable_get(in_runlevel, &FX_CSTR("name"));
|
if (!unit_v || !fx_value_is_type(unit_v, FX_TYPE_HASHTABLE)) {
|
||||||
if (!name_v || !fx_value_is_type(name_v, FX_TYPE_STRING)) {
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
fx_string *name = NULL;
|
fx_hashtable *in_unit = NULL;
|
||||||
fx_value_get_object(name_v, &name);
|
fx_value_get_object(unit_v, &in_unit);
|
||||||
|
|
||||||
const fx_value *description_v
|
const fx_value *description_v
|
||||||
= fx_hashtable_get(in_runlevel, &FX_CSTR("description"));
|
= fx_hashtable_get(in_unit, &FX_CSTR("description"));
|
||||||
if (!description_v
|
if (!description_v
|
||||||
|| !fx_value_is_type(description_v, FX_TYPE_STRING)) {
|
|| !fx_value_is_type(description_v, FX_TYPE_STRING)) {
|
||||||
return -1;
|
return -1;
|
||||||
@@ -52,7 +51,7 @@ static int parse_runlevel_data(fx_object *in, struct runlevel *out)
|
|||||||
fx_value_get_object(description_v, &description);
|
fx_value_get_object(description_v, &description);
|
||||||
|
|
||||||
const fx_value *deps_v
|
const fx_value *deps_v
|
||||||
= fx_hashtable_get(in_runlevel, &FX_CSTR("requires"));
|
= fx_hashtable_get(in_target, &FX_CSTR("requires"));
|
||||||
if (deps_v && !fx_value_is_type(deps_v, FX_TYPE_ARRAY)) {
|
if (deps_v && !fx_value_is_type(deps_v, FX_TYPE_ARRAY)) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@@ -87,15 +86,14 @@ static int parse_runlevel_data(fx_object *in, struct runlevel *out)
|
|||||||
}
|
}
|
||||||
fx_iterator_unref(it);
|
fx_iterator_unref(it);
|
||||||
|
|
||||||
out->rl_name = fx_string_steal(name);
|
|
||||||
out->rl_description = fx_string_steal(description);
|
out->rl_description = fx_string_steal(description);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int runlevel_load(const char *path, struct runlevel **out)
|
int target_load(const char *name, const char *path, struct target **out)
|
||||||
{
|
{
|
||||||
struct runlevel *rl = malloc(sizeof *rl);
|
struct target *rl = malloc(sizeof *rl);
|
||||||
if (!rl) {
|
if (!rl) {
|
||||||
errno = ENOMEM;
|
errno = ENOMEM;
|
||||||
return -1;
|
return -1;
|
||||||
@@ -124,12 +122,14 @@ int runlevel_load(const char *path, struct runlevel **out)
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (parse_runlevel_data(data.v_object, rl) != 0) {
|
if (parse_target_data(data.v_object, rl) != 0) {
|
||||||
free(rl);
|
free(rl);
|
||||||
errno = EFTYPE;
|
errno = EFTYPE;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rl->rl_name = fx_strdup(name);
|
||||||
|
|
||||||
fx_stream_unref(in);
|
fx_stream_unref(in);
|
||||||
fx_value_unset(&data);
|
fx_value_unset(&data);
|
||||||
|
|
||||||
@@ -139,12 +139,12 @@ int runlevel_load(const char *path, struct runlevel **out)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct runlevel *runlevel_find(const char *name)
|
struct target *target_find(const char *name)
|
||||||
{
|
{
|
||||||
struct queue_entry *cur = queue_first(&runlevels);
|
struct queue_entry *cur = queue_first(&targets);
|
||||||
while (cur) {
|
while (cur) {
|
||||||
struct runlevel *rl
|
struct target *rl
|
||||||
= QUEUE_CONTAINER(struct runlevel, rl_entry, cur);
|
= QUEUE_CONTAINER(struct target, rl_entry, cur);
|
||||||
if (!strcmp(rl->rl_name, name)) {
|
if (!strcmp(rl->rl_name, name)) {
|
||||||
return rl;
|
return rl;
|
||||||
}
|
}
|
||||||
@@ -155,7 +155,7 @@ struct runlevel *runlevel_find(const char *name)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int runlevel_activate(struct runlevel *rl)
|
int target_activate(struct target *rl)
|
||||||
{
|
{
|
||||||
for (size_t i = 0; i < rl->rl_requires_count; i++) {
|
for (size_t i = 0; i < rl->rl_requires_count; i++) {
|
||||||
const char *svc_name = rl->rl_requires[i];
|
const char *svc_name = rl->rl_requires[i];
|
||||||
@@ -171,6 +171,6 @@ int runlevel_activate(struct runlevel *rl)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
log_ok("Reached runlevel %s.", rl->rl_description);
|
log_ok("Reached target %s.", rl->rl_description);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
#ifndef TARGET_H_
|
||||||
|
#define TARGET_H_
|
||||||
|
|
||||||
|
#include "queue.h"
|
||||||
|
|
||||||
|
#include <stddef.h>
|
||||||
|
|
||||||
|
struct target {
|
||||||
|
char *rl_name;
|
||||||
|
char *rl_description;
|
||||||
|
char **rl_requires;
|
||||||
|
size_t rl_requires_count;
|
||||||
|
struct queue_entry rl_entry;
|
||||||
|
};
|
||||||
|
|
||||||
|
extern struct queue *global_targets(void);
|
||||||
|
|
||||||
|
extern int target_load(const char *name, const char *path, struct target **out);
|
||||||
|
extern struct target *target_find(const char *name);
|
||||||
|
extern int target_activate(struct target *rl);
|
||||||
|
|
||||||
|
#endif
|
||||||
Reference in New Issue
Block a user