- use this in the busybox template since busybox's init expects to receive SIGUSR1 to halt
- fix lxc.stopsignal to be output by write_config so lxcapi_clone() and lxcapi_save_config() will output it Signed-off-by: Dwight Engen <dwight.en...@oracle.com> --- doc/lxc-stop.sgml.in | 13 ++++++------- src/lxc/conf.h | 3 ++- src/lxc/confile.c | 28 ++++++++++++++++++++++++++++ src/lxc/lxccontainer.c | 5 ++++- templates/lxc-busybox.in | 1 + 5 files changed, 41 insertions(+), 9 deletions(-) diff --git a/doc/lxc-stop.sgml.in b/doc/lxc-stop.sgml.in index bdb0ef5..dc002c5 100644 --- a/doc/lxc-stop.sgml.in +++ b/doc/lxc-stop.sgml.in @@ -65,13 +65,12 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA <para> <command>lxc-stop</command> reboots, cleanly shuts down, or kills all the processes inside the container. By default, it will - request a clean shutdown of the container (by sending SIGPWR to - the container), wait 60 seconds for the container to exit, and - returns. If the container fails to cleanly exit, then after 60 - seconds the container will be sent the - <command>lxc.stopsignal</command> to force it to shut down. If - <command>lxc.stopsignal</command> is not specified, the signal sent is - SIGKILL. + request a clean shutdown of the container by sending + <command>lxc.haltsignal</command> (defaults to SIGPWR) to + the container's init process, waiting up to 60 seconds for the container + to exit, and then returning. If the container fails to cleanly exit in + 60 seconds, it will be sent the <command>lxc.stopsignal</command> + (defaults to SIGKILL) to force it to shut down. </para> <para> The <optional>-W</optional>, <optional>-r</optional>, diff --git a/src/lxc/conf.h b/src/lxc/conf.h index e881635..8efd0f3 100644 --- a/src/lxc/conf.h +++ b/src/lxc/conf.h @@ -307,7 +307,8 @@ struct lxc_conf { #endif int maincmd_fd; int autodev; // if 1, mount and fill a /dev at start - int stopsignal; // signal used to stop container + int haltsignal; // signal used to halt container + int stopsignal; // signal used to hard stop container int kmsg; // if 1, create /dev/kmsg symlink char *rcfile; // Copy of the top level rcfile we read diff --git a/src/lxc/confile.c b/src/lxc/confile.c index 0982b3e..d21fbec 100644 --- a/src/lxc/confile.c +++ b/src/lxc/confile.c @@ -90,6 +90,7 @@ static int config_seccomp(const char *, const char *, struct lxc_conf *); static int config_includefile(const char *, const char *, struct lxc_conf *); static int config_network_nic(const char *, const char *, struct lxc_conf *); static int config_autodev(const char *, const char *, struct lxc_conf *); +static int config_haltsignal(const char *, const char *, struct lxc_conf *); static int config_stopsignal(const char *, const char *, struct lxc_conf *); static int config_start(const char *, const char *, struct lxc_conf *); static int config_group(const char *, const char *, struct lxc_conf *); @@ -142,6 +143,7 @@ static struct lxc_config_t config[] = { { "lxc.seccomp", config_seccomp }, { "lxc.include", config_includefile }, { "lxc.autodev", config_autodev }, + { "lxc.haltsignal", config_haltsignal }, { "lxc.stopsignal", config_stopsignal }, { "lxc.start.auto", config_start }, { "lxc.start.delay", config_start }, @@ -1108,6 +1110,16 @@ static int rt_sig_num(const char *signame) return sig_n; } +static const char *sig_name(int signum) { + int n; + + for (n = 0; n < sizeof(signames) / sizeof((signames)[0]); n++) { + if (n == signames[n].num) + return signames[n].name; + } + return ""; +} + static int sig_parse(const char *signame) { int n; @@ -1125,6 +1137,18 @@ static int sig_parse(const char *signame) { return -1; } +static int config_haltsignal(const char *key, const char *value, + struct lxc_conf *lxc_conf) +{ + int sig_n = sig_parse(value); + + if (sig_n < 0) + return -1; + lxc_conf->haltsignal = sig_n; + + return 0; +} + static int config_stopsignal(const char *key, const char *value, struct lxc_conf *lxc_conf) { @@ -2119,6 +2143,10 @@ void write_config(FILE *fout, struct lxc_conf *c) fprintf(fout, "lxc.pts = %d\n", c->pts); if (c->ttydir) fprintf(fout, "lxc.devttydir = %s\n", c->ttydir); + if (c->haltsignal) + fprintf(fout, "lxc.haltsignal = SIG%s\n", sig_name(c->haltsignal)); + if (c->stopsignal) + fprintf(fout, "lxc.stopsignal = SIG%s\n", sig_name(c->stopsignal)); #if HAVE_SYS_PERSONALITY_H switch(c->personality) { case PER_LINUX32: fprintf(fout, "lxc.arch = x86\n"); break; diff --git a/src/lxc/lxccontainer.c b/src/lxc/lxccontainer.c index 75f6ce3..e066b16 100644 --- a/src/lxc/lxccontainer.c +++ b/src/lxc/lxccontainer.c @@ -1310,6 +1310,7 @@ static bool lxcapi_shutdown(struct lxc_container *c, int timeout) { bool retv; pid_t pid; + int haltsignal = SIGPWR; if (!c) return false; @@ -1321,7 +1322,9 @@ static bool lxcapi_shutdown(struct lxc_container *c, int timeout) pid = c->init_pid(c); if (pid <= 0) return true; - kill(pid, SIGPWR); + if (c->lxc_conf->haltsignal) + haltsignal = c->lxc_conf->haltsignal; + kill(pid, haltsignal); retv = c->wait(c, "STOPPED", timeout); if (!retv && timeout > 0) { c->stop(c); diff --git a/templates/lxc-busybox.in b/templates/lxc-busybox.in index 8232334..974377d 100644 --- a/templates/lxc-busybox.in +++ b/templates/lxc-busybox.in @@ -272,6 +272,7 @@ copy_configuration() grep -q "^lxc.rootfs" $path/config 2>/dev/null || echo "lxc.rootfs = $rootfs" >> $path/config cat <<EOF >> $path/config +lxc.haltsignal = SIGUSR1 lxc.utsname = $name lxc.tty = 1 lxc.pts = 1 -- 1.8.3.1 _______________________________________________ lxc-devel mailing list lxc-devel@lists.linuxcontainers.org http://lists.linuxcontainers.org/listinfo/lxc-devel