Commit e043236e by Michel Normand Committed by Daniel Lezcano

lxc-start to report exit code of started application

The exit code of the application as reported by lxc-start is: 0-126 exit code of the application itself 128+n signal n received by the application 255 lxc error Signed-off-by: 's avatarMichel Normand <normand@fr.ibm.com> Signed-off-by: 's avatarDaniel Lezcano <dlezcano@fr.ibm.com>
parent 41cfbac9
......@@ -23,7 +23,11 @@
#include <stdio.h>
#include <stdlib.h>
#include <sys/wait.h>
#include "error.h"
#include "log.h"
lxc_log_define(lxc_error, lxc);
static const char *const catalogue[] = {
......@@ -67,3 +71,32 @@ const char *const lxc_strerror(int error)
return catalogue[error];
}
/*---------------------------------------------------------------------------*/
/* lxc_error_set_and_log
* function is here to convert
* the reported status to an exit code as detailed here:
*
* 0-126 exit code of the application
* 128+n signal n received by the application
* 255 lxc error
*/
extern int lxc_error_set_and_log(int pid, int status)
{
int ret = 0;
if (WIFEXITED(status)) {
ret = WEXITSTATUS(status);
if (ret)
INFO("child <%d> ended on error (%d)", pid, ret);
}
if (WIFSIGNALED(status)) {
int signal = WTERMSIG(status);
ret = ret + 128 + signal;
INFO("child <%d> ended on signal (%d)", pid, signal);
}
return ret;
}
......@@ -59,4 +59,5 @@ typedef enum {
LXC_LAST_ERROR,
} lxc_error_t;
extern int lxc_error_set_and_log(int pid, int status);
#endif
......@@ -61,7 +61,7 @@ Options :\n\
int main(int argc, char *argv[])
{
char *const *args;
int err;
int err = -1;
struct termios tios;
char *const default_args[] = {
......@@ -69,9 +69,8 @@ int main(int argc, char *argv[])
'\0',
};
err = lxc_arguments_parse(&my_args, argc, argv);
if (err)
return 1;
if (lxc_arguments_parse(&my_args, argc, argv))
return err;
if (!my_args.argc)
args = default_args;
......@@ -80,19 +79,15 @@ int main(int argc, char *argv[])
if (lxc_log_init(my_args.log_file, my_args.log_priority,
my_args.progname, my_args.quiet))
return 1;
return err;
if (tcgetattr(0, &tios)) {
ERROR("failed to get current terminal settings : %s",
strerror(errno));
return 1;
return err;
}
err = lxc_start(my_args.name, args);
if (err) {
ERROR("failed to start '%s'", my_args.name);
err = 1;
}
if (tcsetattr(0, TCSAFLUSH, &tios))
ERROR("failed to restore terminal settings : %s",
......
......@@ -439,7 +439,7 @@ int lxc_spawn(const char *name, struct lxc_handler *handler, char *const argv[])
if (sigprocmask(SIG_SETMASK, &handler->oldmask, NULL)) {
SYSERROR("failed to set sigprocmask");
return -1;
goto out_child;
}
close(sv[1]);
......@@ -460,12 +460,9 @@ int lxc_spawn(const char *name, struct lxc_handler *handler, char *const argv[])
}
/* Setup the container, ip, names, utsname, ... */
err = lxc_setup(name, handler->tty, &handler->tty_info);
if (err) {
if (lxc_setup(name, handler->tty, &handler->tty_info)) {
ERROR("failed to setup the container");
if (write(sv[0], &err, sizeof(err)) < 0)
SYSERROR("failed to write the socket");
goto out_child;
goto out_warn_father;
}
if (prctl(PR_CAPBSET_DROP, CAP_SYS_BOOT, 0, 0, 0)) {
......@@ -476,11 +473,10 @@ int lxc_spawn(const char *name, struct lxc_handler *handler, char *const argv[])
execvp(argv[0], argv);
SYSERROR("failed to exec %s", argv[0]);
err = LXC_ERROR_WRONG_COMMAND;
out_warn_father:
/* If the exec fails, tell that to our father */
if (write(sv[0], &err, sizeof(err)) < 0)
SYSERROR("failed to write the socket");
out_child:
exit(err);
}
......@@ -509,8 +505,7 @@ int lxc_spawn(const char *name, struct lxc_handler *handler, char *const argv[])
}
/* Wait for the child to exec or returning an error */
err = read(sv[1], &sync, sizeof(sync));
if (err < 0) {
if (read(sv[1], &sync, sizeof(sync)) < 0) {
ERROR("failed to read the socket");
goto out_abort;
}
......@@ -542,7 +537,7 @@ out_abort:
int lxc_start(const char *name, char *const argv[])
{
struct lxc_handler handler = { 0 };
int err = -LXC_ERROR_INTERNAL;
int err = -1;
int status;
if (lxc_init(name, &handler)) {
......@@ -556,14 +551,16 @@ int lxc_start(const char *name, char *const argv[])
goto out;
}
if (lxc_poll(name, &handler)) {
err = lxc_poll(name, &handler);
if (err) {
ERROR("mainloop exited with an error");
goto out_abort;
}
while (waitpid(handler.pid, &status, 0) < 0 && errno == EINTR)
continue;
err = 0;
err = lxc_error_set_and_log(handler.pid, status);
out:
lxc_fini(name, &handler);
return err;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment