This patch allows to shutdown the container when the system is powered off in the container.
Signed-off-by: Daniel Lezcano <dlezc...@fr.ibm.com> --- src/lxc/Makefile.am | 6 +- src/lxc/start.c | 11 +++ src/lxc/utmp.c | 156 ++++++++++++++++++++++++++++++++++++++++++++++++++++ src/lxc/utmp.h | 28 +++++++++ 4 files changed, 198 insertions(+), 3 deletions(-) Index: lxc/src/lxc/Makefile.am =================================================================== --- lxc.orig/src/lxc/Makefile.am +++ lxc/src/lxc/Makefile.am @@ -18,7 +18,7 @@ so_PROGRAMS = liblxc.so liblxc_so_SOURCES = \ arguments.c arguments.h \ commands.c commands.h \ - start.c \ + start.c start.h \ stop.c \ monitor.c monitor.h \ console.c \ @@ -43,7 +43,9 @@ liblxc_so_SOURCES = \ genl.c genl.h \ \ mainloop.c mainloop.h \ - af_unix.c af_unix.h + af_unix.c af_unix.h \ + \ + utmp.c utmp.h AM_CFLAGS=-I$(top_srcdir)/src Index: lxc/src/lxc/start.c =================================================================== --- lxc.orig/src/lxc/start.c +++ lxc/src/lxc/start.c @@ -91,10 +91,12 @@ int signalfd(int fd, const sigset_t *mas #include "start.h" #include "conf.h" #include "log.h" +#include "cgroup.h" #include "error.h" #include "af_unix.h" #include "mainloop.h" #include "utils.h" +#include "utmp.h" #include "monitor.h" #include "commands.h" #include "console.h" @@ -172,8 +174,15 @@ int lxc_poll(const char *name, struct lx goto out_mainloop_open; } - if (lxc_command_mainloop_add(name, &descr, handler)) + if (lxc_command_mainloop_add(name, &descr, handler)) { + ERROR("failed to add command handler to mainloop"); goto out_mainloop_open; + } + + if (lxc_utmp_mainloop_add(&descr, handler)) { + ERROR("failed to add utmp handler to mainloop"); + goto out_mainloop_open; + } return lxc_mainloop(&descr); Index: lxc/src/lxc/utmp.c =================================================================== --- /dev/null +++ lxc/src/lxc/utmp.c @@ -0,0 +1,156 @@ +/* + * lxc: linux Container library + * + * (C) Copyright IBM Corp. 2007, 2008 + * + * Authors: + * Daniel Lezcano <dlezcano at fr.ibm.com> + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include <stdio.h> +#include <unistd.h> +#include <errno.h> +#include <signal.h> +#include <stdlib.h> +#include <fcntl.h> +#include <sys/inotify.h> + +#include "conf.h" +#include "cgroup.h" +#include "start.h" +#include "mainloop.h" +#include "lxc.h" +#include "log.h" +#define __USE_GNU +#include <utmpx.h> +#undef __USE_GNU + +lxc_log_define(lxc_utmp, lxc); + +static int utmp_handler(int fd, void *data, struct lxc_epoll_descr *descr) +{ + struct inotify_event ie; + struct utmpx *utmpx; + struct lxc_handler *handler = (struct lxc_handler *)data; + struct lxc_conf *conf = handler->conf; + char prevrun_level = 'N', currun_level = 'N'; + int ntasks, ret; + char path[MAXPATHLEN]; + + if (read(fd, &ie, sizeof(ie)) < 0) { + SYSERROR("failed to read utmp notification"); + return -1; + } + + if (snprintf(path, MAXPATHLEN, "%s/var/run/utmp", conf->rootfs) > + MAXPATHLEN) { + ERROR("path is too long"); + return -1; + } + + if (utmpxname(path)) { + SYSERROR("failed to 'utmpxname'"); + return -1; + } + + setutxent(); + + while ((utmpx = getutxent())) { + + if (utmpx->ut_type == RUN_LVL) { + prevrun_level = utmpx->ut_pid / 256; + currun_level = utmpx->ut_pid % 256; + } + } + + ntasks = lxc_cgroup_nrtasks(handler->name); + if (ntasks < 0) { + ERROR("failed to get the number of tasks"); + goto out; + } + + if (ntasks == 1 && prevrun_level == '3') { + + DEBUG("run level is %c/%c", prevrun_level, currun_level); + DEBUG("there is %d tasks remaining", ntasks); + + if (currun_level == '0') { + INFO("container has shutdown"); + kill(handler->pid, SIGKILL); + } + + if (currun_level == '6') { + INFO("container has reboot"); + kill(handler->pid, SIGKILL); + } + } + + ret = 0; +out: + endutxent(); + + return ret; +} + +int lxc_utmp_mainloop_add(struct lxc_epoll_descr *descr, + struct lxc_handler *handler) +{ + struct lxc_conf *conf = handler->conf; + char path[MAXPATHLEN]; + int fd, wd; + + if (!conf->rootfs) + return 0; + + if (snprintf(path, MAXPATHLEN, "%s/var/run/utmp", conf->rootfs) > + MAXPATHLEN) { + ERROR("path is too long"); + return -1; + } + + if (access(path, F_OK)) { + WARN("'%s' not found", path); + return 0; + } + + fd = inotify_init(); + if (fd < 0) { + SYSERROR("failed to inotify_init"); + return -1; + } + + if (fcntl(fd, F_SETFD, FD_CLOEXEC)) { + SYSERROR("failed to set inotify fd to close-on-exec"); + close(fd); + return -1; + } + + wd = inotify_add_watch(fd, path, IN_MODIFY); + if (wd < 0) { + SYSERROR("failed to add watch for '%s'", path); + close(fd); + return -1; + } + + if (lxc_mainloop_add_handler(descr, fd, utmp_handler, handler)) { + SYSERROR("failed to add mainloop"); + close(fd); + return -1; + } + + return 0; +} Index: lxc/src/lxc/utmp.h =================================================================== --- /dev/null +++ lxc/src/lxc/utmp.h @@ -0,0 +1,28 @@ +/* + * lxc: linux Container library + * + * (C) Copyright IBM Corp. 2007, 2008 + * + * Authors: + * Daniel Lezcano <dlezcano at fr.ibm.com> + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +struct lxc_handler; +struct lxc_epoll_descr; + +int lxc_utmp_mainloop_add(struct lxc_epoll_descr *descr, + struct lxc_handler *handler); ------------------------------------------------------------------------------ The Planet: dedicated and managed hosting, cloud storage, colocation Stay online with enterprise data centers and the best network in the business Choose flexible plans and management services without long-term contracts Personal 24x7 support from experience hosting pros just a phone call away. http://p.sf.net/sfu/theplanet-com _______________________________________________ Lxc-devel mailing list Lxc-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/lxc-devel