Add support for finit <stop|start|reload|restart> JOB

This patch further extends the capabilities of the client with the
ability to control the running state of services:

    finit <stop|start|reload|restart> JOB

Since services can now exist with multiple instances the concept of
"jobs" is introduced in this patch.  A job is a numeric identifier of
the form `NUM[:NUM]`, the latter `:NUM` is the new instance syntax
introduced earlier.  See the output of `finit status` for the JOB id.

Also, with the introduction of multiple instances we broke support for
multiple related inetd services.  This became obvious when the shiny new
`finit status` was tested ... hence, this patch also contains fixes to
the inetd support.

Signed-off-by: Joachim Nilsson <troglobit@gmail.com>
This commit is contained in:
Joachim Nilsson
2015-06-08 08:32:49 +02:00
parent 720324b256
commit 24e1d284ad
7 changed files with 296 additions and 93 deletions
+64 -2
View File
@@ -53,6 +53,48 @@ static void fifo_open(void)
}
}
static svc_t *convert_jobid(char *jobid)
{
int job, id = 1;
char *token;
if (!jobid)
return NULL;
token = strtok(jobid, ":");
if (!token) {
job = atoi(jobid);
} else {
job = atoi(token);
token = strtok(NULL, "");
if (token)
id = atoi(token);
}
_d("Got job %d id %d ...", job, id);
return svc_find_by_jobid(job, id);
}
static int do_start(char *jobid)
{
return service_start(convert_jobid(jobid));
}
static int do_stop(char *jobid)
{
return service_stop(convert_jobid(jobid));
}
static int do_reload(char *jobid)
{
return service_reload(convert_jobid(jobid));
}
static int do_restart(char *jobid)
{
return service_restart(convert_jobid(jobid));
}
/* Standard reboot/shutdown utilities talk to init using /dev/initctl.
* We should check if the fifo was recreated and reopen it.
*/
@@ -62,6 +104,7 @@ static void parse(void *UNUSED(arg), int fd, int UNUSED(events))
_d("Receiving request on descriptor %d, from %s ...", fd, FINIT_FIFO);
while (1) {
int result = 0;
ssize_t len = read(fd, &rq, sizeof(rq));
if (len <= 0) {
@@ -125,6 +168,22 @@ static void parse(void *UNUSED(arg), int fd, int UNUSED(events))
reload_finit_d();
break;
case INIT_CMD_START_SVC:
result = do_start(rq.data);
break;
case INIT_CMD_STOP_SVC:
result = do_stop(rq.data);
break;
case INIT_CMD_RELOAD_SVC:
result = do_reload(rq.data);
break;
case INIT_CMD_RESTART_SVC:
result = do_restart(rq.data);
break;
case INIT_CMD_ACK:
_d("Client failed reading ACK.");
goto leave;
@@ -134,10 +193,13 @@ static void parse(void *UNUSED(arg), int fd, int UNUSED(events))
break;
}
rq.cmd = INIT_CMD_ACK;
if (result)
rq.cmd = INIT_CMD_NACK;
else
rq.cmd = INIT_CMD_ACK;
len = write(fd, &rq, sizeof(rq));
if (len != sizeof(rq))
_d("Failed sending ACK back to client.");
_d("Failed sending ACK/NACK back to client.");
else
sleep(1); /* Give client time to read FIFO */
}