Added several fields to process-control status operation: active, description, command, status, starttime, pid
This commit is contained in:
parent
7e9a207ab2
commit
07d196dfd0
8 changed files with 144 additions and 58 deletions
|
|
@ -39,7 +39,7 @@ Expected: April
|
||||||
* The netconf client will terminate (close the socket) if the client does not comply
|
* The netconf client will terminate (close the socket) if the client does not comply
|
||||||
* You can set `CLICON_NETCONF_HELLO_OPTIONAL` to true to use the old behavior of essentially ignoring hellos.
|
* You can set `CLICON_NETCONF_HELLO_OPTIONAL` to true to use the old behavior of essentially ignoring hellos.
|
||||||
* New clixon-lib@2020-03-08.yang revision
|
* New clixon-lib@2020-03-08.yang revision
|
||||||
* Changed: RPC process-control output to choice dependent on operation
|
* Changed: RPC process-control output to choice with status fields
|
||||||
* New clixon-config@2020-03-08.yang revision
|
* New clixon-config@2020-03-08.yang revision
|
||||||
* Added: `CLICON_NETCONF_HELLO_OPTIONAL`
|
* Added: `CLICON_NETCONF_HELLO_OPTIONAL`
|
||||||
|
|
||||||
|
|
@ -55,6 +55,7 @@ Developers may need to change their code
|
||||||
|
|
||||||
### Minor features
|
### Minor features
|
||||||
|
|
||||||
|
* Added several fields to process-control status operation: active, description, command, status, starttime, pid
|
||||||
* Changed signal handling
|
* Changed signal handling
|
||||||
* Moved clixon-proc sigchild handling from handler to clixon_events
|
* Moved clixon-proc sigchild handling from handler to clixon_events
|
||||||
* The base capability has been changed to "urn:ietf:params:netconf:base:1.1" following RFC6241.
|
* The base capability has been changed to "urn:ietf:params:netconf:base:1.1" following RFC6241.
|
||||||
|
|
|
||||||
|
|
@ -1584,7 +1584,6 @@ from_client_process_control(clicon_handle h,
|
||||||
cxobj *x;
|
cxobj *x;
|
||||||
char *name = NULL;
|
char *name = NULL;
|
||||||
char *opstr = NULL;
|
char *opstr = NULL;
|
||||||
uint32_t pid = 0;
|
|
||||||
proc_operation op = PROC_OP_NONE;
|
proc_operation op = PROC_OP_NONE;
|
||||||
|
|
||||||
if ((x = xml_find_type(xe, NULL, "name", CX_ELMNT)) != NULL)
|
if ((x = xml_find_type(xe, NULL, "name", CX_ELMNT)) != NULL)
|
||||||
|
|
@ -1594,16 +1593,16 @@ from_client_process_control(clicon_handle h,
|
||||||
op = clixon_process_op_str2int(opstr);
|
op = clixon_process_op_str2int(opstr);
|
||||||
}
|
}
|
||||||
/* Make the actual process operation (with wrap function enabled) */
|
/* Make the actual process operation (with wrap function enabled) */
|
||||||
if (clixon_process_operation(h, name, op, 1, &pid) < 0)
|
if (op == PROC_OP_STATUS){
|
||||||
goto done;
|
if (clixon_process_status(h, name, cbret) < 0)
|
||||||
if (op == PROC_OP_STATUS)
|
goto done;
|
||||||
cprintf(cbret, "<rpc-reply xmlns=\"%s\"><status xmlns=\"%s\">%s</status><pid xmlns=\"%s\">%u</pid></rpc-reply>",
|
}
|
||||||
NETCONF_BASE_NAMESPACE,
|
else{
|
||||||
CLIXON_LIB_NS, pid?"true":"false",
|
if (clixon_process_operation(h, name, op, 1) < 0)
|
||||||
CLIXON_LIB_NS, pid);
|
goto done;
|
||||||
else
|
|
||||||
cprintf(cbret, "<rpc-reply xmlns=\"%s\"><ok xmlns=\"%s\"/></rpc-reply>",
|
cprintf(cbret, "<rpc-reply xmlns=\"%s\"><ok xmlns=\"%s\"/></rpc-reply>",
|
||||||
NETCONF_BASE_NAMESPACE, CLIXON_LIB_NS);
|
NETCONF_BASE_NAMESPACE, CLIXON_LIB_NS);
|
||||||
|
}
|
||||||
retval = 0;
|
retval = 0;
|
||||||
done:
|
done:
|
||||||
return retval;
|
return retval;
|
||||||
|
|
|
||||||
|
|
@ -137,6 +137,7 @@ restconf_pseudo_process_control(clicon_handle h)
|
||||||
argv[i++] = NULL;
|
argv[i++] = NULL;
|
||||||
assert(i==nr);
|
assert(i==nr);
|
||||||
if (clixon_process_register(h, RESTCONF_PROCESS,
|
if (clixon_process_register(h, RESTCONF_PROCESS,
|
||||||
|
"Clixon RESTCONF process",
|
||||||
NULL /* XXX network namespace */,
|
NULL /* XXX network namespace */,
|
||||||
restconf_rpc_wrapper,
|
restconf_rpc_wrapper,
|
||||||
argv, nr) < 0)
|
argv, nr) < 0)
|
||||||
|
|
@ -196,7 +197,7 @@ restconf_pseudo_process_commit(clicon_handle h,
|
||||||
if ((cx = xpath_first(xtarget, NULL, "/restconf/enable")) != NULL &&
|
if ((cx = xpath_first(xtarget, NULL, "/restconf/enable")) != NULL &&
|
||||||
xml_flag(cx, XML_FLAG_CHANGE|XML_FLAG_ADD)){
|
xml_flag(cx, XML_FLAG_CHANGE|XML_FLAG_ADD)){
|
||||||
if (clixon_process_operation(h, RESTCONF_PROCESS,
|
if (clixon_process_operation(h, RESTCONF_PROCESS,
|
||||||
enabled?PROC_OP_START:PROC_OP_STOP, 0, NULL) < 0)
|
enabled?PROC_OP_START:PROC_OP_STOP, 0) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
else if (enabled){ /* If something changed and running, restart process */
|
else if (enabled){ /* If something changed and running, restart process */
|
||||||
|
|
@ -209,7 +210,7 @@ restconf_pseudo_process_commit(clicon_handle h,
|
||||||
* Specifically, the socket is terminated where the reply is sent, which will
|
* Specifically, the socket is terminated where the reply is sent, which will
|
||||||
* cause the curl to fail.
|
* cause the curl to fail.
|
||||||
*/
|
*/
|
||||||
if (clixon_process_operation(h, RESTCONF_PROCESS, PROC_OP_RESTART, 0, NULL) < 0)
|
if (clixon_process_operation(h, RESTCONF_PROCESS, PROC_OP_RESTART, 0) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -62,9 +62,10 @@ int clixon_proc_socket(char **argv, pid_t *pid, int *sock);
|
||||||
int clixon_proc_socket_close(pid_t pid, int sock);
|
int clixon_proc_socket_close(pid_t pid, int sock);
|
||||||
int clixon_proc_background(char **argv, const char *netns, pid_t *pid);
|
int clixon_proc_background(char **argv, const char *netns, pid_t *pid);
|
||||||
proc_operation clixon_process_op_str2int(char *opstr);
|
proc_operation clixon_process_op_str2int(char *opstr);
|
||||||
int clixon_process_register(clicon_handle h, const char *name, const char *netns, proc_cb_t *callback, char **argv, int argc);
|
int clixon_process_register(clicon_handle h, const char *name, const char *descr, const char *netns, proc_cb_t *callback, char **argv, int argc);
|
||||||
int clixon_process_delete_all(clicon_handle h);
|
int clixon_process_delete_all(clicon_handle h);
|
||||||
int clixon_process_operation(clicon_handle h, const char *name, proc_operation op, const int wrapit, uint32_t *pid);
|
int clixon_process_operation(clicon_handle h, const char *name, proc_operation op, const int wrapit);
|
||||||
|
int clixon_process_status(clicon_handle h, const char *name, cbuf *cbret);
|
||||||
int clixon_process_start_all(clicon_handle h);
|
int clixon_process_start_all(clicon_handle h);
|
||||||
int clixon_process_sched_register(clicon_handle h);
|
int clixon_process_sched_register(clicon_handle h);
|
||||||
int clixon_process_waitpid(clicon_handle h);
|
int clixon_process_waitpid(clicon_handle h);
|
||||||
|
|
|
||||||
|
|
@ -52,6 +52,8 @@
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <sys/time.h>
|
#include <sys/time.h>
|
||||||
|
|
||||||
|
#include <cligen/cligen.h>
|
||||||
|
|
||||||
#include "clixon_queue.h"
|
#include "clixon_queue.h"
|
||||||
#include "clixon_log.h"
|
#include "clixon_log.h"
|
||||||
#include "clixon_hash.h"
|
#include "clixon_hash.h"
|
||||||
|
|
|
||||||
|
|
@ -71,10 +71,14 @@
|
||||||
#include "clixon_queue.h"
|
#include "clixon_queue.h"
|
||||||
#include "clixon_hash.h"
|
#include "clixon_hash.h"
|
||||||
#include "clixon_handle.h"
|
#include "clixon_handle.h"
|
||||||
|
#include "clixon_options.h"
|
||||||
#include "clixon_event.h"
|
#include "clixon_event.h"
|
||||||
#include "clixon_sig.h"
|
#include "clixon_sig.h"
|
||||||
#include "clixon_string.h"
|
#include "clixon_string.h"
|
||||||
#include "clixon_queue.h"
|
#include "clixon_queue.h"
|
||||||
|
#include "clixon_yang.h"
|
||||||
|
#include "clixon_xml.h"
|
||||||
|
#include "clixon_netconf_lib.h"
|
||||||
#include "clixon_proc.h"
|
#include "clixon_proc.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
@ -85,6 +89,7 @@
|
||||||
struct process_entry_t {
|
struct process_entry_t {
|
||||||
qelem_t pe_qelem; /* List header */
|
qelem_t pe_qelem; /* List header */
|
||||||
char *pe_name; /* Name of process used for internal use. Unique with exiting=0 */
|
char *pe_name; /* Name of process used for internal use. Unique with exiting=0 */
|
||||||
|
char *pe_description; /* Description of service */
|
||||||
char *pe_netns; /* Network namespace */
|
char *pe_netns; /* Network namespace */
|
||||||
char **pe_argv; /* argv with command as element 0 and NULL-terminated */
|
char **pe_argv; /* argv with command as element 0 and NULL-terminated */
|
||||||
int pe_argc; /* Length of argc */
|
int pe_argc; /* Length of argc */
|
||||||
|
|
@ -93,6 +98,7 @@ struct process_entry_t {
|
||||||
int pe_clone; /* Duplicate when restarting, delete when reaped */
|
int pe_clone; /* Duplicate when restarting, delete when reaped */
|
||||||
pid_t pe_status; /* Status on exit as defined in waitpid */
|
pid_t pe_status; /* Status on exit as defined in waitpid */
|
||||||
proc_operation pe_op; /* Operation pending? */
|
proc_operation pe_op; /* Operation pending? */
|
||||||
|
struct timeval pe_starttime; /* Start time */
|
||||||
proc_cb_t *pe_callback; /* Wrapper function, may be called from process_operation */
|
proc_cb_t *pe_callback; /* Wrapper function, may be called from process_operation */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
@ -336,6 +342,10 @@ clixon_process_register_dup(process_entry_t *pe0,
|
||||||
clicon_err(OE_DB, errno, "strdup name");
|
clicon_err(OE_DB, errno, "strdup name");
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
if (pe0->pe_description && (pe1->pe_description = strdup(pe0->pe_description)) == NULL){
|
||||||
|
clicon_err(OE_DB, errno, "strdup name");
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
if (pe0->pe_netns && (pe1->pe_netns = strdup(pe0->pe_netns)) == NULL){
|
if (pe0->pe_netns && (pe1->pe_netns = strdup(pe0->pe_netns)) == NULL){
|
||||||
clicon_err(OE_DB, errno, "strdup netns");
|
clicon_err(OE_DB, errno, "strdup netns");
|
||||||
goto done;
|
goto done;
|
||||||
|
|
@ -363,6 +373,7 @@ clixon_process_register_dup(process_entry_t *pe0,
|
||||||
*
|
*
|
||||||
* @param[in] h Clixon handle
|
* @param[in] h Clixon handle
|
||||||
* @param[in] name Process name
|
* @param[in] name Process name
|
||||||
|
* @param[in] description Description of process
|
||||||
* @param[in] netns Namespace netspace (or NULL)
|
* @param[in] netns Namespace netspace (or NULL)
|
||||||
* @param[in] callback
|
* @param[in] callback
|
||||||
* @param[in] argv NULL-terminated vector of vectors
|
* @param[in] argv NULL-terminated vector of vectors
|
||||||
|
|
@ -374,6 +385,7 @@ clixon_process_register_dup(process_entry_t *pe0,
|
||||||
int
|
int
|
||||||
clixon_process_register(clicon_handle h,
|
clixon_process_register(clicon_handle h,
|
||||||
const char *name,
|
const char *name,
|
||||||
|
const char *description,
|
||||||
const char *netns,
|
const char *netns,
|
||||||
proc_cb_t *callback,
|
proc_cb_t *callback,
|
||||||
char **argv,
|
char **argv,
|
||||||
|
|
@ -400,6 +412,10 @@ clixon_process_register(clicon_handle h,
|
||||||
clicon_err(OE_DB, errno, "strdup name");
|
clicon_err(OE_DB, errno, "strdup name");
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
if (description && (pe->pe_description = strdup(description)) == NULL){
|
||||||
|
clicon_err(OE_DB, errno, "strdup description");
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
if (netns && (pe->pe_netns = strdup(netns)) == NULL){
|
if (netns && (pe->pe_netns = strdup(netns)) == NULL){
|
||||||
clicon_err(OE_DB, errno, "strdup netns");
|
clicon_err(OE_DB, errno, "strdup netns");
|
||||||
goto done;
|
goto done;
|
||||||
|
|
@ -430,6 +446,8 @@ clixon_process_delete_only(process_entry_t *pe)
|
||||||
|
|
||||||
if (pe->pe_name)
|
if (pe->pe_name)
|
||||||
free(pe->pe_name);
|
free(pe->pe_name);
|
||||||
|
if (pe->pe_description)
|
||||||
|
free(pe->pe_description);
|
||||||
if (pe->pe_netns)
|
if (pe->pe_netns)
|
||||||
free(pe->pe_netns);
|
free(pe->pe_netns);
|
||||||
if (pe->pe_argv){
|
if (pe->pe_argv){
|
||||||
|
|
@ -488,13 +506,12 @@ proc_op_run(pid_t pid0,
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*! Find process operation entry given name and op and perform operation if found
|
/*! Find process entry given name and schedule operation
|
||||||
*
|
*
|
||||||
* @param[in] h clicon handle
|
* @param[in] h clicon handle
|
||||||
* @param[in] name Name of process
|
* @param[in] name Name of process
|
||||||
* @param[in] op start, stop, restart, status
|
* @param[in] op start, stop, restart, status
|
||||||
* @param[in] wrapit If set, call potential callback, if false, dont call it
|
* @param[in] wrapit If set, call potential callback, if false, dont call it
|
||||||
* @param[out] pid >0 process# and is running / 0: not running
|
|
||||||
* @retval -1 Error
|
* @retval -1 Error
|
||||||
* @retval 0 OK
|
* @retval 0 OK
|
||||||
* @see upgrade_callback_reg_fn which registers the callbacks
|
* @see upgrade_callback_reg_fn which registers the callbacks
|
||||||
|
|
@ -507,8 +524,7 @@ int
|
||||||
clixon_process_operation(clicon_handle h,
|
clixon_process_operation(clicon_handle h,
|
||||||
const char *name,
|
const char *name,
|
||||||
proc_operation op,
|
proc_operation op,
|
||||||
int wrapit,
|
int wrapit)
|
||||||
uint32_t *pid)
|
|
||||||
{
|
{
|
||||||
int retval = -1;
|
int retval = -1;
|
||||||
process_entry_t *pe;
|
process_entry_t *pe;
|
||||||
|
|
@ -520,25 +536,16 @@ clixon_process_operation(clicon_handle h,
|
||||||
pe = _proc_entry_list;
|
pe = _proc_entry_list;
|
||||||
do {
|
do {
|
||||||
if (strcmp(pe->pe_name, name) == 0){
|
if (strcmp(pe->pe_name, name) == 0){
|
||||||
if (op == PROC_OP_STATUS){
|
/* Call wrapper function that eg changes op based on config */
|
||||||
if (pe->pe_clone)
|
if (wrapit && pe->pe_callback != NULL)
|
||||||
continue; /* this may be a dying duplicate */
|
if (pe->pe_callback(h, pe, &op) < 0)
|
||||||
if (pid)
|
goto done;
|
||||||
*pid = pe->pe_pid;
|
clicon_debug(1, "%s name: %s pid:%d op: %s", __FUNCTION__,
|
||||||
}
|
name, pe->pe_pid, clicon_int2str(proc_operation_map, op));
|
||||||
else {
|
if (op == PROC_OP_START || op == PROC_OP_STOP || op == PROC_OP_RESTART){
|
||||||
/* Call wrapper function that eg changes op based on config */
|
pe->pe_op = op;
|
||||||
if (wrapit && pe->pe_callback != NULL)
|
clicon_debug(1, "%s scheduling %s pid:%d", __FUNCTION__, name, pe->pe_pid);
|
||||||
if (pe->pe_callback(h, pe, &op) < 0)
|
sched++;
|
||||||
goto done;
|
|
||||||
clicon_debug(1, "%s name: %s pid:%d op: %s", __FUNCTION__,
|
|
||||||
name, pe->pe_pid, clicon_int2str(proc_operation_map, op));
|
|
||||||
if (op == PROC_OP_START || op == PROC_OP_STOP || op == PROC_OP_RESTART){
|
|
||||||
pe->pe_op = op;
|
|
||||||
clicon_debug(1, "%s scheduling %s pid:%d", __FUNCTION__, name, pe->pe_pid);
|
|
||||||
sched++;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
break; /* hit break here */
|
break; /* hit break here */
|
||||||
}
|
}
|
||||||
|
|
@ -553,6 +560,66 @@ clixon_process_operation(clicon_handle h,
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*! Get process status according to clixon-lib.yang
|
||||||
|
*
|
||||||
|
* @param[in] h clicon handle
|
||||||
|
* @param[in] name Name of process
|
||||||
|
* @param[out] cbret XML status string
|
||||||
|
* @retval -1 Error
|
||||||
|
* @retval 0 OK
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
clixon_process_status(clicon_handle h,
|
||||||
|
const char *name,
|
||||||
|
cbuf *cbret)
|
||||||
|
|
||||||
|
{
|
||||||
|
int retval = -1;
|
||||||
|
process_entry_t *pe;
|
||||||
|
int run;
|
||||||
|
int i;
|
||||||
|
char timestr[28];
|
||||||
|
|
||||||
|
if (_proc_entry_list == NULL)
|
||||||
|
goto ok;
|
||||||
|
pe = _proc_entry_list;
|
||||||
|
do {
|
||||||
|
if (strcmp(pe->pe_name, name) == 0){
|
||||||
|
if (pe->pe_clone)
|
||||||
|
continue; /* this may be a dying duplicate */
|
||||||
|
/* Check if running */
|
||||||
|
run = 0;
|
||||||
|
if (pe->pe_pid && proc_op_run(pe->pe_pid, &run) < 0)
|
||||||
|
goto done;
|
||||||
|
cprintf(cbret, "<rpc-reply xmlns=\"%s\"><active xmlns=\"%s\">%s</active>",
|
||||||
|
NETCONF_BASE_NAMESPACE, CLIXON_LIB_NS, run?"true":"false");
|
||||||
|
if (pe->pe_description)
|
||||||
|
cprintf(cbret, "<description xmlns=\"%s\">%s</description>", CLIXON_LIB_NS, pe->pe_description);
|
||||||
|
if (pe->pe_pid)
|
||||||
|
cprintf(cbret, "<pid xmlns=\"%s\">%u</pid>", CLIXON_LIB_NS, pe->pe_pid);
|
||||||
|
cprintf(cbret, "<command xmlns=\"%s\">", CLIXON_LIB_NS);
|
||||||
|
for (i=0; i<pe->pe_argc-1; i++){
|
||||||
|
if (i)
|
||||||
|
cprintf(cbret, " ");
|
||||||
|
cprintf(cbret, "%s", pe->pe_argv[i]);
|
||||||
|
}
|
||||||
|
cprintf(cbret, "</command>");
|
||||||
|
cprintf(cbret, "<status xmlns=\"%s\">%u</status>", CLIXON_LIB_NS, pe->pe_status);
|
||||||
|
if (run && time2str(pe->pe_starttime, timestr, sizeof(timestr)) < 0)
|
||||||
|
goto done;
|
||||||
|
cprintf(cbret, "<starttime xmlns=\"%s\">%s</starttime>", CLIXON_LIB_NS, timestr);
|
||||||
|
cprintf(cbret, "</rpc-reply>");
|
||||||
|
break; /* hit break here */
|
||||||
|
}
|
||||||
|
pe = NEXTQ(process_entry_t *, pe);
|
||||||
|
} while (pe != _proc_entry_list);
|
||||||
|
ok:
|
||||||
|
retval = 0;
|
||||||
|
done:
|
||||||
|
clicon_debug(1, "%s retval:%d", __FUNCTION__, retval);
|
||||||
|
return retval;
|
||||||
|
}
|
||||||
|
|
||||||
/*! Go through process list and start all processes that are enabled via config wrap function
|
/*! Go through process list and start all processes that are enabled via config wrap function
|
||||||
* @param[in] h Clixon handle
|
* @param[in] h Clixon handle
|
||||||
* Commit rules should have done this, but there are some cases such as backend -s none mode
|
* Commit rules should have done this, but there are some cases such as backend -s none mode
|
||||||
|
|
@ -623,7 +690,6 @@ clixon_process_sched(int fd,
|
||||||
pe->pe_exiting == 0){
|
pe->pe_exiting == 0){
|
||||||
/* Check if running */
|
/* Check if running */
|
||||||
run = 0;
|
run = 0;
|
||||||
clicon_debug(1, "%s run: %d", __FUNCTION__, run);
|
|
||||||
if (proc_op_run(pe->pe_pid, &run) < 0)
|
if (proc_op_run(pe->pe_pid, &run) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
switch (op){
|
switch (op){
|
||||||
|
|
@ -642,6 +708,7 @@ clixon_process_sched(int fd,
|
||||||
break;
|
break;
|
||||||
if (clixon_proc_background(pe->pe_argv, pe->pe_netns, &newpid) < 0)
|
if (clixon_proc_background(pe->pe_argv, pe->pe_netns, &newpid) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
|
gettimeofday(&pe->pe_starttime, NULL);
|
||||||
clicon_debug(1, "%s restart pid:%d -> %d", __FUNCTION__, pe->pe_pid, newpid);
|
clicon_debug(1, "%s restart pid:%d -> %d", __FUNCTION__, pe->pe_pid, newpid);
|
||||||
/* Create a new pe */
|
/* Create a new pe */
|
||||||
if (clixon_process_register_dup(pe, &pe1) < 0)
|
if (clixon_process_register_dup(pe, &pe1) < 0)
|
||||||
|
|
@ -655,6 +722,7 @@ clixon_process_sched(int fd,
|
||||||
break;
|
break;
|
||||||
if (clixon_proc_background(pe->pe_argv, pe->pe_netns, &pe->pe_pid) < 0)
|
if (clixon_proc_background(pe->pe_argv, pe->pe_netns, &pe->pe_pid) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
|
gettimeofday(&pe->pe_starttime, NULL);
|
||||||
clicon_debug(1, "%s started pid:%d", __FUNCTION__, pe->pe_pid);
|
clicon_debug(1, "%s started pid:%d", __FUNCTION__, pe->pe_pid);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
|
|
||||||
|
|
@ -76,22 +76,18 @@ $DEFAULTHELLO
|
||||||
EOF
|
EOF
|
||||||
)
|
)
|
||||||
|
|
||||||
expect1="<rpc-reply $DEFAULTNS><pid xmlns=\"http://clicon.org/lib\">"
|
|
||||||
match=$(echo "$ret" | grep --null -Go "$expect1")
|
|
||||||
if [ -z "$match" ]; then
|
|
||||||
err "$expect1" "$ret"
|
|
||||||
fi
|
|
||||||
|
|
||||||
# >&2 echo "ret:$ret" # debug
|
# >&2 echo "ret:$ret" # debug
|
||||||
|
|
||||||
expect2="</pid></rpc-reply>]]>]]>"
|
expect1="<pid xmlns=\"http://clicon.org/lib\">[0-9]*</pid>"
|
||||||
match=$(echo "$ret" | grep --null -Go "$expect2")
|
match=$(echo "$ret" | grep --null -Go "$expect1")
|
||||||
|
# >&2 echo "match:$match" # debug
|
||||||
if [ -z "$match" ]; then
|
if [ -z "$match" ]; then
|
||||||
err "$expect2" "$ret"
|
pid=0
|
||||||
|
else
|
||||||
|
pid=$(echo "$match" | awk -F'[<>]' '{print $3}')
|
||||||
fi
|
fi
|
||||||
new "check rpc $operation get pid"
|
|
||||||
pid=$(echo "$ret" | awk -F'[<>]' '{print $5}')
|
|
||||||
>&2 echo "pid:$pid" # debug
|
>&2 echo "pid:$pid" # debug
|
||||||
|
|
||||||
if [ -z "$pid" ]; then
|
if [ -z "$pid" ]; then
|
||||||
err "Running process" "$ret"
|
err "Running process" "$ret"
|
||||||
fi
|
fi
|
||||||
|
|
@ -107,9 +103,9 @@ EOF
|
||||||
err "Running process"
|
err "Running process"
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
echo "$pid" # cant use return that only uses 0-255
|
||||||
fi
|
fi
|
||||||
sleep $DEMSLEEP
|
sleep $DEMSLEEP
|
||||||
echo "$pid" # cant use return that only uses 0-255
|
|
||||||
}
|
}
|
||||||
|
|
||||||
new "ENABLE true"
|
new "ENABLE true"
|
||||||
|
|
@ -141,8 +137,8 @@ if [ $BE -ne 0 ]; then
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# For debug
|
# For debug
|
||||||
>&2 echo "curl $CURLOPTS -X POST -H \"Content-Type: application/yang-data+json\" $RCPROTO://localhost/restconf/operations/clixon-lib:process-control -d '{\"clixon-lib:input\":{\"name\":\"restconf\",\"operation\":\"status\"}}'"
|
#>&2 echo "curl $CURLOPTS -X POST -H \"Content-Type: application/yang-data+json\" $RCPROTO://localhost/restconf/operations/clixon-lib:process-control -d '{\"clixon-lib:input\":{\"name\":\"restconf\",\"operation\":\"status\"}}'"
|
||||||
exit
|
|
||||||
# Get pid of running process and check return xml
|
# Get pid of running process and check return xml
|
||||||
new "1. Get rpc status"
|
new "1. Get rpc status"
|
||||||
pid0=$(testrpc status 1) # Save pid0
|
pid0=$(testrpc status 1) # Save pid0
|
||||||
|
|
@ -165,7 +161,7 @@ new "wait restconf"
|
||||||
wait_restconf
|
wait_restconf
|
||||||
|
|
||||||
new "try restconf rpc status"
|
new "try restconf rpc status"
|
||||||
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/operations/clixon-lib:process-control -d '{"clixon-lib:input":{"name":"restconf","operation":"status"}}')" 0 "HTTP/1.1 200 OK" '{"clixon-lib:output":{"pid":'
|
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/operations/clixon-lib:process-control -d '{"clixon-lib:input":{"name":"restconf","operation":"status"}}')" 0 "HTTP/1.1 200 OK" '{"clixon-lib:output":' '"active":' '"pid":'
|
||||||
|
|
||||||
new "2. Get status"
|
new "2. Get status"
|
||||||
pid1=$(testrpc status 1)
|
pid1=$(testrpc status 1)
|
||||||
|
|
@ -177,7 +173,7 @@ if [ "$pid0" -ne "$pid1" ]; then
|
||||||
fi
|
fi
|
||||||
|
|
||||||
new "try restconf rpc restart"
|
new "try restconf rpc restart"
|
||||||
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/operations/clixon-lib:process-control -d '{"clixon-lib:input":{"name":"restconf","operation":"restart"}}')" 0 "HTTP/1.1 200 OK" '{"clixon-lib:output":{"pid":'
|
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/operations/clixon-lib:process-control -d '{"clixon-lib:input":{"name":"restconf","operation":"restart"}}')" 0 "HTTP/1.1 204 No Content"
|
||||||
|
|
||||||
new "3. Get status"
|
new "3. Get status"
|
||||||
pid1=$(testrpc status 1)
|
pid1=$(testrpc status 1)
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,9 @@ module clixon-lib {
|
||||||
namespace "http://clicon.org/lib";
|
namespace "http://clicon.org/lib";
|
||||||
prefix cl;
|
prefix cl;
|
||||||
|
|
||||||
|
import ietf-yang-types {
|
||||||
|
prefix yang;
|
||||||
|
}
|
||||||
organization
|
organization
|
||||||
"Clicon / Clixon";
|
"Clicon / Clixon";
|
||||||
|
|
||||||
|
|
@ -178,13 +181,28 @@ module clixon-lib {
|
||||||
case status {
|
case status {
|
||||||
description
|
description
|
||||||
"Output from status rpc";
|
"Output from status rpc";
|
||||||
leaf status {
|
leaf active {
|
||||||
description "True if process is running, false if not";
|
description "True if process is running, false if not";
|
||||||
type boolean;
|
type boolean;
|
||||||
}
|
}
|
||||||
|
leaf description {
|
||||||
|
type string;
|
||||||
|
description "Description of process. This is a static string";
|
||||||
|
}
|
||||||
|
leaf command {
|
||||||
|
type string;
|
||||||
|
description "Start command with arguments";
|
||||||
|
}
|
||||||
|
leaf status {
|
||||||
|
description "Exit Status as defined by waitpid() - if exited";
|
||||||
|
type int32;
|
||||||
|
}
|
||||||
|
leaf starttime {
|
||||||
|
description "Time of starting process UTC";
|
||||||
|
type yang:date-and-time;
|
||||||
|
}
|
||||||
leaf pid {
|
leaf pid {
|
||||||
description "Process-id of running process or 0 if not running
|
description "Process-id of main running process (if active)";
|
||||||
Value is only valid for operation status";
|
|
||||||
type uint32;
|
type uint32;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue