#include <pwd.h>
#include <sys/mount.h>
#include <linux/fs.h>
+#include <linux/oom.h>
#ifdef HAVE_PAM
#include <security/pam_appl.h>
#include "cgroup.h"
#include "namespace.h"
#include "tcpwrap.h"
+#include "exit-status.h"
+#include "missing.h"
+#include "utmp-wtmp.h"
/* This assumes there is a 'tty' group */
#define TTY_MODE 0620
sa.sa.sa_family = AF_UNIX;
strncpy(sa.un.sun_path+1, LOGGER_SOCKET, sizeof(sa.un.sun_path)-1);
- if (connect(fd, &sa.sa, sizeof(sa_family_t) + 1 + sizeof(LOGGER_SOCKET) - 1) < 0) {
+ if (connect(fd, &sa.sa, offsetof(struct sockaddr_un, sun_path) + 1 + sizeof(LOGGER_SOCKET) - 1) < 0) {
close_nointr_nofail(fd);
return -errno;
}
goto fail;
}
+ /* If a socket is connected to STDIN/STDOUT/STDERR, we
+ * must sure to drop O_NONBLOCK */
+ if (socket_fd >= 0)
+ fd_nonblock(socket_fd, false);
+
if (!keep_stdin)
if (setup_input(context, socket_fd, apply_tty_stdin) < 0) {
r = EXIT_STDIN;
goto fail;
}
- if (context->oom_adjust_set) {
+ if (context->oom_score_adjust_set) {
char t[16];
- snprintf(t, sizeof(t), "%i", context->oom_adjust);
+ snprintf(t, sizeof(t), "%i", context->oom_score_adjust);
char_array_0(t);
- if (write_one_line_file("/proc/self/oom_adj", t) < 0) {
- r = EXIT_OOM_ADJUST;
- goto fail;
+ if (write_one_line_file("/proc/self/oom_score_adj", t) < 0) {
+ /* Compatibility with Linux <= 2.6.35 */
+
+ int adj;
+
+ adj = (context->oom_score_adjust * -OOM_DISABLE) / OOM_SCORE_ADJ_MAX;
+ adj = CLAMP(adj, OOM_DISABLE, OOM_ADJUST_MAX);
+
+ snprintf(t, sizeof(t), "%i", adj);
+ char_array_0(t);
+
+ if (write_one_line_file("/proc/self/oom_adj", t) < 0) {
+ r = EXIT_OOM_ADJUST;
+ goto fail;
+ }
}
}
goto fail;
}
+ if (context->utmp_id)
+ utmp_put_init_process(0, context->utmp_id, getpid(), getsid(0), context->tty_path);
+
if (context->user) {
username = context->user;
if (get_user_creds(&username, &uid, &gid, &home) < 0) {
"%sNice: %i\n",
prefix, c->nice);
- if (c->oom_adjust_set)
+ if (c->oom_score_adjust_set)
fprintf(f,
- "%sOOMAdjust: %i\n",
- prefix, c->oom_adjust);
+ "%sOOMScoreAdjust: %i\n",
+ prefix, c->oom_score_adjust);
for (i = 0; i < RLIM_NLIMITS; i++)
if (c->rlimit[i])
"%sKillSignal: SIG%s\n",
prefix, kill_mode_to_string(c->kill_mode),
prefix, signal_to_string(c->kill_signal));
+
+ if (c->utmp_id)
+ fprintf(f,
+ "%sUtmpIdentifier: %s\n",
+ prefix, c->utmp_id);
}
void exec_status_start(ExecStatus *s, pid_t pid) {
dual_timestamp_get(&s->start_timestamp);
}
-void exec_status_exit(ExecStatus *s, pid_t pid, int code, int status) {
+void exec_status_exit(ExecStatus *s, pid_t pid, int code, int status, const char *utmp_id) {
assert(s);
if ((s->pid && s->pid != pid) ||
s->code = code;
s->status = status;
+
+ if (utmp_id)
+ utmp_put_dead_process(utmp_id, pid, code, status);
}
void exec_status_dump(ExecStatus *s, FILE *f, const char *prefix) {
return 0;
}
-const char* exit_status_to_string(ExitStatus status) {
-
- /* We cast to int here, so that -Wenum doesn't complain that
- * EXIT_SUCCESS/EXIT_FAILURE aren't in the enum */
-
- switch ((int) status) {
-
- case EXIT_SUCCESS:
- return "SUCCESS";
-
- case EXIT_FAILURE:
- return "FAILURE";
-
- case EXIT_INVALIDARGUMENT:
- return "INVALIDARGUMENT";
-
- case EXIT_NOTIMPLEMENTED:
- return "NOTIMPLEMENTED";
-
- case EXIT_NOPERMISSION:
- return "NOPERMISSION";
-
- case EXIT_NOTINSTALLED:
- return "NOTINSSTALLED";
-
- case EXIT_NOTCONFIGURED:
- return "NOTCONFIGURED";
-
- case EXIT_NOTRUNNING:
- return "NOTRUNNING";
-
- case EXIT_CHDIR:
- return "CHDIR";
-
- case EXIT_NICE:
- return "NICE";
-
- case EXIT_FDS:
- return "FDS";
-
- case EXIT_EXEC:
- return "EXEC";
-
- case EXIT_MEMORY:
- return "MEMORY";
-
- case EXIT_LIMITS:
- return "LIMITS";
-
- case EXIT_OOM_ADJUST:
- return "OOM_ADJUST";
-
- case EXIT_SIGNAL_MASK:
- return "SIGNAL_MASK";
-
- case EXIT_STDIN:
- return "STDIN";
-
- case EXIT_STDOUT:
- return "STDOUT";
-
- case EXIT_CHROOT:
- return "CHROOT";
-
- case EXIT_IOPRIO:
- return "IOPRIO";
-
- case EXIT_TIMERSLACK:
- return "TIMERSLACK";
-
- case EXIT_SECUREBITS:
- return "SECUREBITS";
-
- case EXIT_SETSCHEDULER:
- return "SETSCHEDULER";
-
- case EXIT_CPUAFFINITY:
- return "CPUAFFINITY";
-
- case EXIT_GROUP:
- return "GROUP";
-
- case EXIT_USER:
- return "USER";
-
- case EXIT_CAPABILITIES:
- return "CAPABILITIES";
-
- case EXIT_CGROUP:
- return "CGROUP";
-
- case EXIT_SETSID:
- return "SETSID";
-
- case EXIT_CONFIRM:
- return "CONFIRM";
-
- case EXIT_STDERR:
- return "STDERR";
-
- case EXIT_TCPWRAP:
- return "TCPWRAP";
-
- case EXIT_PAM:
- return "PAM";
-
- default:
- return NULL;
- }
-}
-
static const char* const exec_input_table[_EXEC_INPUT_MAX] = {
[EXEC_INPUT_NULL] = "null",
[EXEC_INPUT_TTY] = "tty",