Bump procd version 2017.02.08

This commit is contained in:
2017-03-18 22:42:48 +01:00
parent a08515f4a7
commit 7195cc3d28
17 changed files with 208 additions and 44 deletions

View File

@@ -4,13 +4,13 @@
#
################################################################################
PROCD_VERSION:= 2016.07.29
PROCD_VERSION:= 2017.02.08
PROCD_SITE = $(TOPDIR)/../../src/3P/procd/builders/cmake
PROCD_SITE_METHOD = local
PROCD_INSTALL_STAGING = YES
PROCD_DEPENDENCIES = libubox json-c ubus
PROCD_DEPENDENCIES = libubox ubus json-c
PROCD_CONF = SRC_DIR=$(TOPDIR)/../..

View File

@@ -28,7 +28,7 @@ ENDIF()
SET(LIBS ubox ubus json-c blobmsg_json json_script)
IF(DEBUG)
ADD_DEFINITIONS(-DDEBUG -g3)
ADD_DEFINITIONS(-DUDEV_DEBUG -g3)
ENDIF()
IF(EARLY_PATH)

View File

@@ -18,7 +18,7 @@
#include <sys/reboot.h>
#include <libubox/uloop.h>
#include <ubus/libubus.h>
#include <libubus.h>
#include <limits.h>
#include <stdlib.h>

View File

@@ -121,5 +121,6 @@ int mkdev(const char *name, int _mode)
n_patterns = 1;
find_devs(true);
find_devs(false);
free(pattern);
return chdir("/");
}

View File

@@ -19,7 +19,7 @@
#include <libubox/uloop.h>
#include <libubox/utils.h>
#include <ubus/libubus.h>
#include <libubus.h>
#include <stdio.h>

View File

@@ -124,5 +124,11 @@ mount_zram_on_tmp(void)
LOG("Using up to %ld kB of RAM as ZRAM storage on /mnt\n", zramsize);
ret = chmod("/tmp", 01777);
if (ret < 0) {
ERROR("Can't set /tmp mode to 1777: %s\n", strerror(errno));
return errno;
}
return 0;
}

View File

@@ -12,7 +12,7 @@
* GNU General Public License for more details.
*/
//AWOX #define _GNU_SOURCE
#define _GNU_SOURCE
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/ioctl.h>
@@ -31,6 +31,10 @@
#include "procd.h"
#include "rcS.h"
#ifndef O_PATH
#define O_PATH 010000000
#endif
#define TAG_ID 0
#define TAG_RUNLVL 1
#define TAG_ACTION 2
@@ -224,6 +228,14 @@ static struct init_handler handlers[] = {
.name = "respawn",
.cb = rcrespawn,
.multi = 1,
}, {
.name = "askconsolelate",
.cb = askconsole,
.multi = 1,
}, {
.name = "respawnlate",
.cb = rcrespawn,
.multi = 1,
}
};

View File

@@ -25,6 +25,7 @@
#include <libgen.h>
#include <sched.h>
#include <linux/limits.h>
#include <signal.h>
#include "capabilities.h"
#include "elf.h"
@@ -269,8 +270,14 @@ static int exec_jail(void *_notused)
static int jail_running = 1;
static int jail_return_code = 0;
static void jail_process_timeout_cb(struct uloop_timeout *t);
static struct uloop_timeout jail_process_timeout = {
.cb = jail_process_timeout_cb,
};
static void jail_process_handler(struct uloop_process *c, int ret)
{
uloop_timeout_cancel(&jail_process_timeout);
if (WIFEXITED(ret)) {
jail_return_code = WEXITSTATUS(ret);
INFO("jail (%d) exited with exit: %d\n", c->pid, jail_return_code);
@@ -286,12 +293,25 @@ static struct uloop_process jail_process = {
.cb = jail_process_handler,
};
static void jail_process_timeout_cb(struct uloop_timeout *t)
{
DEBUG("jail process failed to stop, sending SIGKILL\n");
kill(jail_process.pid, SIGKILL);
}
static void jail_handle_signal(int signo)
{
DEBUG("forwarding signal %d to the jailed process\n", signo);
kill(jail_process.pid, signo);
}
int main(int argc, char **argv)
{
sigset_t sigmask;
uid_t uid = getuid();
char log[] = "/dev/log";
char ubus[] = "/var/run/ubus.sock";
int ch;
int ch, i;
if (uid) {
ERROR("not root, aborting: %s\n", strerror(errno));
@@ -385,7 +405,26 @@ int main(int argc, char **argv)
prctl(PR_SET_NAME, opts.name, NULL, NULL, NULL);
uloop_init();
sigfillset(&sigmask);
for (i = 0; i < _NSIG; i++) {
struct sigaction s = { 0 };
if (!sigismember(&sigmask, i))
continue;
if ((i == SIGCHLD) || (i == SIGPIPE))
continue;
s.sa_handler = jail_handle_signal;
sigaction(i, &s, NULL);
}
if (opts.namespace) {
add_mount("/dev/full", 0, -1);
add_mount("/dev/null", 0, -1);
add_mount("/dev/urandom", 0, -1);
add_mount("/dev/zero", 0, -1);
int flags = CLONE_NEWPID | CLONE_NEWNS | CLONE_NEWIPC | SIGCHLD;
if (opts.hostname)
flags |= CLONE_NEWUTS;
@@ -398,12 +437,13 @@ int main(int argc, char **argv)
/* parent process */
uloop_process_add(&jail_process);
uloop_run();
uloop_done();
if (jail_running) {
DEBUG("uloop interrupted, killing jail process\n");
kill(jail_process.pid, SIGTERM);
waitpid(jail_process.pid, NULL, 0);
uloop_timeout_set(&jail_process_timeout, 1000);
uloop_run();
}
uloop_done();
return jail_return_code;
} else if (jail_process.pid == 0) {
/* fork child process */

View File

@@ -130,6 +130,7 @@ static void handle_makedev(struct blob_attr *msg, struct blob_attr *data)
char *minor = hotplug_msg_find_var(msg, "MINOR");
char *major = hotplug_msg_find_var(msg, "MAJOR");
char *subsystem = hotplug_msg_find_var(msg, "SUBSYSTEM");
int ret = 0;
blobmsg_parse_array(mkdev_policy, 3, tb, blobmsg_data(data), blobmsg_data_len(data));
if (tb[0] && tb[1] && minor && major && subsystem) {
@@ -149,8 +150,9 @@ static void handle_makedev(struct blob_attr *msg, struct blob_attr *data)
struct group *g = getgrnam(blobmsg_get_string(tb[2]));
if (g)
chown(blobmsg_get_string(tb[0]), 0, g->gr_gid);
else
ret = chown(blobmsg_get_string(tb[0]), 0, g->gr_gid);
if (!g || ret < 0)
ERROR("cannot set group %s for %s\n",
blobmsg_get_string(tb[2]),
blobmsg_get_string(tb[0]));

View File

@@ -66,7 +66,7 @@ static void log_message(int priority, const char *format, ...)
log_message(LOG_INFO ,"%s: " format ,__FUNCTION__ ,## arg); \
} while (0)
#ifdef DEBUG
#ifdef UDEV_DEBUG
#undef dbg
#define dbg(format, arg...) \
do { \

View File

@@ -17,7 +17,7 @@
#include <libubox/uloop.h>
#include <libubox/utils.h>
#include <ubus/libubus.h>
#include <libubus.h>
#include <stdio.h>
#include <syslog.h>

View File

@@ -12,7 +12,7 @@
* GNU General Public License for more details.
*/
//AWOX #define _GNU_SOURCE
#define _GNU_SOURCE
#include <sys/resource.h>
#include <sys/types.h>
#include <sys/socket.h>
@@ -54,6 +54,7 @@ enum {
INSTANCE_ATTR_TRACE,
INSTANCE_ATTR_SECCOMP,
INSTANCE_ATTR_PIDFILE,
INSTANCE_ATTR_RELOADSIG,
__INSTANCE_ATTR_MAX
};
@@ -77,6 +78,7 @@ static const struct blobmsg_policy instance_attr[__INSTANCE_ATTR_MAX] = {
[INSTANCE_ATTR_TRACE] = { "trace", BLOBMSG_TYPE_BOOL },
[INSTANCE_ATTR_SECCOMP] = { "seccomp", BLOBMSG_TYPE_STRING },
[INSTANCE_ATTR_PIDFILE] = { "pidfile", BLOBMSG_TYPE_STRING },
[INSTANCE_ATTR_RELOADSIG] = { "reload_signal", BLOBMSG_TYPE_INT32 },
};
enum {
@@ -263,6 +265,7 @@ instance_writepid(struct service_instance *in)
if (fprintf(_pidfile, "%d\n", in->proc.pid) < 0) {
ERROR("failed to write pidfile: %s: %d (%s)",
in->pidfile, errno, strerror(errno));
fclose(_pidfile);
return 2;
}
if (fclose(_pidfile)) {
@@ -386,7 +389,7 @@ instance_start(struct service_instance *in)
return;
}
if (in->proc.pending)
if (in->proc.pending || !in->command)
return;
instance_free_stdio(in);
@@ -526,7 +529,9 @@ instance_exit(struct uloop_process *p, int ret)
in->srv->name, in->name, in->respawn_count, runtime);
in->restart = in->respawn = 0;
in->halt = 1;
service_event("instance.fail", in->srv->name, in->name);
} else {
service_event("instance.respawn", in->srv->name, in->name);
uloop_timeout_set(&in->timeout, in->respawn_timeout * 1000);
}
}
@@ -548,6 +553,12 @@ instance_restart(struct service_instance *in)
{
if (!in->proc.pending)
return;
if (in->reload_signal) {
kill(in->proc.pid, in->reload_signal);
return;
}
in->halt = false;
in->restart = true;
kill(in->proc.pid, SIGTERM);
@@ -566,9 +577,6 @@ instance_config_changed(struct service_instance *in, struct service_instance *in
if (!blobmsg_list_equal(&in->env, &in_new->env))
return true;
if (!blobmsg_list_equal(&in->data, &in_new->data))
return true;
if (!blobmsg_list_equal(&in->netdev, &in_new->netdev))
return true;
@@ -751,31 +759,42 @@ instance_jail_parse(struct service_instance *in, struct blob_attr *attr)
}
static bool
instance_config_parse(struct service_instance *in)
instance_config_parse_command(struct service_instance *in, struct blob_attr **tb)
{
struct blob_attr *tb[__INSTANCE_ATTR_MAX];
struct blob_attr *cur, *cur2;
int argc = 0;
bool ret = false;
int rem;
blobmsg_parse(instance_attr, __INSTANCE_ATTR_MAX, tb,
blobmsg_data(in->config), blobmsg_data_len(in->config));
cur = tb[INSTANCE_ATTR_COMMAND];
if (!cur)
return false;
if (!cur) {
in->command = NULL;
return true;
}
if (!blobmsg_check_attr_list(cur, BLOBMSG_TYPE_STRING))
return false;
blobmsg_for_each_attr(cur2, cur, rem) {
argc++;
ret = true;
break;
}
if (!argc)
return false;
in->command = cur;
return ret;
}
static bool
instance_config_parse(struct service_instance *in)
{
struct blob_attr *tb[__INSTANCE_ATTR_MAX];
struct blob_attr *cur, *cur2;
int rem;
blobmsg_parse(instance_attr, __INSTANCE_ATTR_MAX, tb,
blobmsg_data(in->config), blobmsg_data_len(in->config));
if (!instance_config_parse_command(in, tb))
return false;
if (tb[INSTANCE_ATTR_RESPAWN]) {
int i = 0;
@@ -843,6 +862,9 @@ instance_config_parse(struct service_instance *in)
in->pidfile = pidfile;
}
if (tb[INSTANCE_ATTR_RELOADSIG])
in->reload_signal = blobmsg_get_u32(tb[INSTANCE_ATTR_RELOADSIG]);
if (!in->trace && tb[INSTANCE_ATTR_JAIL])
in->has_jail = instance_jail_parse(in, tb[INSTANCE_ATTR_JAIL]);
@@ -906,25 +928,21 @@ instance_config_move(struct service_instance *in, struct service_instance *in_sr
in_src->config = NULL;
}
bool
void
instance_update(struct service_instance *in, struct service_instance *in_new)
{
bool changed = instance_config_changed(in, in_new);
bool running = in->proc.pending;
if (!changed && running)
return false;
if (!running) {
if (changed)
instance_config_move(in, in_new);
instance_start(in);
} else {
if (changed)
instance_restart(in);
instance_config_move(in, in_new);
/* restart happens in the child callback handler */
}
return true;
}
void
@@ -979,6 +997,7 @@ void instance_dump(struct blob_buf *b, struct service_instance *in, int verbose)
blobmsg_add_u8(b, "running", in->proc.pending);
if (in->proc.pending)
blobmsg_add_u32(b, "pid", in->proc.pid);
if (in->command)
blobmsg_add_blob(b, in->command);
if (!avl_is_empty(&in->errors.avl)) {
@@ -1013,6 +1032,9 @@ void instance_dump(struct blob_buf *b, struct service_instance *in, int verbose)
blobmsg_close_table(b, e);
}
if (in->reload_signal)
blobmsg_add_u32(b, "reload_signal", in->reload_signal);
if (in->respawn) {
void *r = blobmsg_open_table(b, "respawn");
blobmsg_add_u32(b, "threshold", in->respawn_threshold);

View File

@@ -49,6 +49,7 @@ struct service_instance {
bool restart;
bool respawn;
int respawn_count;
int reload_signal;
struct timespec start;
bool trace;
@@ -80,7 +81,7 @@ struct service_instance {
void instance_start(struct service_instance *in);
void instance_stop(struct service_instance *in);
bool instance_update(struct service_instance *in, struct service_instance *in_new);
void instance_update(struct service_instance *in, struct service_instance *in_new);
void instance_init(struct service_instance *in, struct service *s, struct blob_attr *config);
void instance_free(struct service_instance *in);
void instance_dump(struct blob_buf *b, struct service_instance *in, int debug);

View File

@@ -189,6 +189,19 @@ static const struct blobmsg_policy service_list_attrs[__SERVICE_LIST_ATTR_MAX] =
[SERVICE_LIST_ATTR_VERBOSE] = { "verbose", BLOBMSG_TYPE_BOOL },
};
enum {
SERVICE_SIGNAL_ATTR_NAME,
SERVICE_SIGNAL_ATTR_INSTANCE,
SERVICE_SIGNAL_ATTR_SIGNAL,
__SERVICE_SIGNAL_ATTR_MAX,
};
static const struct blobmsg_policy service_signal_attrs[__SERVICE_SIGNAL_ATTR_MAX] = {
[SERVICE_SIGNAL_ATTR_NAME] = { "name", BLOBMSG_TYPE_STRING },
[SERVICE_SIGNAL_ATTR_INSTANCE] = { "instance", BLOBMSG_TYPE_STRING },
[SERVICE_SIGNAL_ATTR_SIGNAL] = { "signal", BLOBMSG_TYPE_INT32 },
};
enum {
EVENT_TYPE,
EVENT_DATA,
@@ -353,6 +366,63 @@ service_handle_delete(struct ubus_context *ctx, struct ubus_object *obj,
return 0;
}
static int
service_handle_kill(struct service_instance *in, int sig)
{
if (kill(in->proc.pid, sig) == 0)
return 0;
switch (errno) {
case EINVAL: return UBUS_STATUS_INVALID_ARGUMENT;
case EPERM: return UBUS_STATUS_PERMISSION_DENIED;
case ESRCH: return UBUS_STATUS_NOT_FOUND;
}
return UBUS_STATUS_UNKNOWN_ERROR;
}
static int
service_handle_signal(struct ubus_context *ctx, struct ubus_object *obj,
struct ubus_request_data *req, const char *method,
struct blob_attr *msg)
{
struct blob_attr *tb[__SERVICE_SIGNAL_ATTR_MAX], *cur;
struct service *s;
struct service_instance *in;
int sig = SIGHUP;
int rv = 0;
blobmsg_parse(service_signal_attrs, __SERVICE_SIGNAL_ATTR_MAX, tb, blob_data(msg), blob_len(msg));
cur = tb[SERVICE_SIGNAL_ATTR_SIGNAL];
if (cur)
sig = blobmsg_get_u32(cur);
cur = tb[SERVICE_SIGNAL_ATTR_NAME];
if (!cur)
return UBUS_STATUS_NOT_FOUND;
s = avl_find_element(&services, blobmsg_data(cur), s, avl);
if (!s)
return UBUS_STATUS_NOT_FOUND;
cur = tb[SERVICE_SIGNAL_ATTR_INSTANCE];
if (!cur) {
vlist_for_each_element(&s->instances, in, node)
rv = service_handle_kill(in, sig);
return rv;
}
in = vlist_find(&s->instances, blobmsg_data(cur), in, node);
if (!in) {
ERROR("instance %s not found\n", blobmsg_get_string(cur));
return UBUS_STATUS_NOT_FOUND;
}
return service_handle_kill(in, sig);
}
static int
service_handle_update(struct ubus_context *ctx, struct ubus_object *obj,
struct ubus_request_data *req, const char *method,
@@ -363,7 +433,7 @@ service_handle_update(struct ubus_context *ctx, struct ubus_object *obj,
blobmsg_parse(service_attrs, __SERVICE_ATTR_MAX, tb, blob_data(msg), blob_len(msg));
cur = tb[SERVICE_ATTR_NAME];
cur = tb[SERVICE_SET_NAME];
if (!cur)
return UBUS_STATUS_INVALID_ARGUMENT;
@@ -490,6 +560,7 @@ static struct ubus_method main_object_methods[] = {
UBUS_METHOD("add", service_handle_set, service_set_attrs),
UBUS_METHOD("list", service_handle_list, service_list_attrs),
UBUS_METHOD("delete", service_handle_delete, service_del_attrs),
UBUS_METHOD("signal", service_handle_signal, service_signal_attrs),
UBUS_METHOD("update_start", service_handle_update, service_attrs),
UBUS_METHOD("update_complete", service_handle_update, service_attrs),
UBUS_METHOD("event", service_handle_event, event_policy),

View File

@@ -128,6 +128,8 @@ static void state_enter(void)
case STATE_RUNNING:
LOG("- init complete -\n");
procd_inittab_run("respawnlate");
procd_inittab_run("askconsolelate");
break;
case STATE_SHUTDOWN:

View File

@@ -176,7 +176,7 @@ int main(int argc, char **argv, char **envp)
if (child == 0) {
char **_argv = calloc(argc + 1, sizeof(char *));
char **_envp;
char preload[] = "LD_PRELOAD=/lib/libpreload-trace.so";
char *preload = "LD_PRELOAD=/lib/libpreload-trace.so";
int envc = 1;
int ret;
@@ -187,10 +187,13 @@ int main(int argc, char **argv, char **envp)
_envp = calloc(envc, sizeof(char *));
memcpy(&_envp[1], _envp, envc * sizeof(char *));
*envp = preload;
*_envp = preload;
ret = execve(_argv[0], _argv, envp);
ret = execve(_argv[0], _argv, _envp);
ERROR("failed to exec %s: %s\n", _argv[0], strerror(errno));
free(_argv);
free(_envp);
return ret;
}

View File

@@ -12,7 +12,7 @@
* GNU General Public License for more details.
*/
//AWOX #define _GNU_SOURCE
#define _GNU_SOURCE
#include <libubox/avl.h>
#include <libubox/avl-cmp.h>
#include "utils.h"
@@ -26,6 +26,10 @@
#include "../log.h"
#ifndef O_PATH
#define O_PATH 010000000
#endif
void
__blobmsg_list_init(struct blobmsg_list *list, int offset, int len, blobmsg_list_cmp cmp)
{