checked in (request 38331)
OBS-URL: https://build.opensuse.org/package/show/Base:System/sysvinit?expand=0&rev=41
This commit is contained in:
parent
3afec739d5
commit
a7646a3a3e
@ -1,212 +0,0 @@
|
|||||||
--- src/Makefile
|
|
||||||
+++ src/Makefile 2010-04-13 00:00:00.000000000 +0000
|
|
||||||
@@ -8,7 +8,7 @@
|
|
||||||
# Version: @(#)Makefile 2.85-13 23-Mar-2004 miquels@cistron.nl
|
|
||||||
#
|
|
||||||
|
|
||||||
-CPPFLAGS =
|
|
||||||
+CPPFLAGS = -DUSE_PAM
|
|
||||||
CFLAGS ?= -ansi -O2 -fomit-frame-pointer
|
|
||||||
override CFLAGS += -W -Wall -D_GNU_SOURCE
|
|
||||||
STATIC =
|
|
||||||
@@ -78,6 +78,13 @@ else
|
|
||||||
endif
|
|
||||||
|
|
||||||
# Additional libs for GNU libc.
|
|
||||||
+ifneq ($(findstring -DUSE_PAM,$(CPPFLAGS)),)
|
|
||||||
+ INITLIBS += -lpam
|
|
||||||
+ PAMDOTD = /etc/pam.d
|
|
||||||
+ PAMINIT = $(PAMDOTD)/init
|
|
||||||
+endif
|
|
||||||
+
|
|
||||||
+# Additional libs for GNU libc.
|
|
||||||
ifneq ($(wildcard /usr/lib*/libcrypt.a),)
|
|
||||||
SULOGINLIBS += -lcrypt
|
|
||||||
endif
|
|
||||||
@@ -149,6 +156,11 @@ install:
|
|
||||||
for i in $(USRBIN); do \
|
|
||||||
$(INSTALL_EXEC) $$i $(ROOT)/usr/bin/ ; \
|
|
||||||
done
|
|
||||||
+ifneq ($(findstring -DUSE_PAM,$(CPPFLAGS)),)
|
|
||||||
+ $(INSTALL_DIR) $(ROOT)$(PAMDOTD)
|
|
||||||
+ test -s $(ROOT)$(PAMINIT) || \
|
|
||||||
+ $(INSTALL_DATA) init.sample $(ROOT)$(PAMINIT)
|
|
||||||
+endif
|
|
||||||
# $(INSTALL_DIR) $(ROOT)/etc/
|
|
||||||
# $(INSTALL_EXEC) initscript.sample $(ROOT)/etc/
|
|
||||||
ln -sf halt $(ROOT)/sbin/reboot
|
|
||||||
--- src/init.c
|
|
||||||
+++ src/init.c 2010-04-13 00:00:00.000000000 +0000
|
|
||||||
@@ -79,6 +79,10 @@
|
|
||||||
#include "reboot.h"
|
|
||||||
#include "set.h"
|
|
||||||
|
|
||||||
+#ifdef USE_PAM
|
|
||||||
+extern void notify_pam_dead_session(const char *id);
|
|
||||||
+#endif
|
|
||||||
+
|
|
||||||
#ifndef SIGPWR
|
|
||||||
# define SIGPWR SIGUSR2
|
|
||||||
#endif
|
|
||||||
@@ -1132,6 +1136,9 @@ pid_t spawn(CHILD *ch, int *res)
|
|
||||||
}
|
|
||||||
dup(f);
|
|
||||||
dup(f);
|
|
||||||
+#ifdef USE_PAM
|
|
||||||
+ notify_pam_dead_session(ch->id);
|
|
||||||
+#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
@@ -1551,6 +1558,9 @@ void read_inittab(void)
|
|
||||||
INITDBG(L_VB, "Updating utmp for pid %d [id %s]",
|
|
||||||
ch->pid, ch->id);
|
|
||||||
ch->flags &= ~RUNNING;
|
|
||||||
+#ifdef USE_PAM
|
|
||||||
+ notify_pam_dead_session(ch->id);
|
|
||||||
+#endif
|
|
||||||
if (ch->process[0] != '+')
|
|
||||||
write_utmp_wtmp("", ch->id, ch->pid, DEAD_PROCESS, NULL);
|
|
||||||
}
|
|
||||||
@@ -2012,6 +2022,9 @@ void re_exec(void)
|
|
||||||
if (ch->flags & ZOMBIE) {
|
|
||||||
INITDBG(L_VB, "Child died, PID= %d", ch->pid);
|
|
||||||
ch->flags &= ~(RUNNING|ZOMBIE|WAITING);
|
|
||||||
+#ifdef USE_PAM
|
|
||||||
+ notify_pam_dead_session(ch->id);
|
|
||||||
+#endif
|
|
||||||
if (ch->process[0] != '+')
|
|
||||||
write_utmp_wtmp("", ch->id, ch->pid, DEAD_PROCESS, NULL);
|
|
||||||
}
|
|
||||||
@@ -2465,6 +2478,9 @@ void process_signals()
|
|
||||||
if (ch->flags & ZOMBIE) {
|
|
||||||
INITDBG(L_VB, "Child died, PID= %d", ch->pid);
|
|
||||||
ch->flags &= ~(RUNNING|ZOMBIE|WAITING);
|
|
||||||
+#ifdef USE_PAM
|
|
||||||
+ notify_pam_dead_session(ch->id);
|
|
||||||
+#endif
|
|
||||||
if (ch->process[0] != '+')
|
|
||||||
write_utmp_wtmp("", ch->id, ch->pid, DEAD_PROCESS, NULL);
|
|
||||||
}
|
|
||||||
--- src/init.sample
|
|
||||||
+++ src/init.sample 2010-04-13 00:00:00.000000000 +0000
|
|
||||||
@@ -0,0 +1,9 @@
|
|
||||||
+#%PAM-1.0
|
|
||||||
+#
|
|
||||||
+# The PAM configuration file for /sbin/init
|
|
||||||
+# Used for updating the lastlog logging file
|
|
||||||
+#
|
|
||||||
+auth sufficient pam_rootok.so
|
|
||||||
+account include common-account
|
|
||||||
+session include common-session
|
|
||||||
+session requisite pam_lastlog.so silent
|
|
||||||
--- src/utmp.c
|
|
||||||
+++ src/utmp.c 2010-04-13 00:00:00.000000000 +0000
|
|
||||||
@@ -34,10 +34,18 @@
|
|
||||||
#include <string.h>
|
|
||||||
#include <utmp.h>
|
|
||||||
|
|
||||||
+#if defined(USE_PAM) && defined(INIT_MAIN)
|
|
||||||
+# include <security/pam_appl.h>
|
|
||||||
+# include <security/pam_misc.h>
|
|
||||||
+#endif
|
|
||||||
+
|
|
||||||
#include "init.h"
|
|
||||||
#include "initreq.h"
|
|
||||||
#include "paths.h"
|
|
||||||
|
|
||||||
+#ifndef _PATH_DEV
|
|
||||||
+# define _PATH_DEV "/dev/"
|
|
||||||
+#endif
|
|
||||||
|
|
||||||
#if defined(__GLIBC__)
|
|
||||||
# if (__GLIBC__ == 2) && (__GLIBC_MINOR__ == 0) && defined(__powerpc__)
|
|
||||||
@@ -127,9 +135,9 @@ char *line) /* Which line is this */
|
|
||||||
strncpy(utmp.ut_name, user, sizeof(utmp.ut_name));
|
|
||||||
strncpy(utmp.ut_id , id , sizeof(utmp.ut_id ));
|
|
||||||
strncpy(utmp.ut_line, line, sizeof(utmp.ut_line));
|
|
||||||
-
|
|
||||||
- /* Put the OS version in place of the hostname */
|
|
||||||
- if (uname(&uname_buf) == 0)
|
|
||||||
+
|
|
||||||
+ /* Put the OS version in place of the hostname */
|
|
||||||
+ if (uname(&uname_buf) == 0)
|
|
||||||
strncpy(utmp.ut_host, uname_buf.release, sizeof(utmp.ut_host));
|
|
||||||
|
|
||||||
#if HAVE_UPDWTMP
|
|
||||||
@@ -262,3 +270,75 @@ char *line) /* LINE if used. */
|
|
||||||
write_wtmp(user, id, pid, type, line && line[0] ? line : oldline);
|
|
||||||
}
|
|
||||||
|
|
||||||
+#if defined(USE_PAM) && defined(INIT_MAIN)
|
|
||||||
+static pam_handle_t *pamh = NULL;
|
|
||||||
+# ifdef __GNUC__
|
|
||||||
+static int
|
|
||||||
+null_conv(int num_msg, const struct pam_message **msgm,
|
|
||||||
+ struct pam_response **response __attribute__((unused)),
|
|
||||||
+ void *appdata_ptr __attribute__((unused)))
|
|
||||||
+# else
|
|
||||||
+static int
|
|
||||||
+null_conv(int num_msg, const struct pam_message **msgm,
|
|
||||||
+ struct pam_response **response, void *appdata_ptr)
|
|
||||||
+# endif
|
|
||||||
+{
|
|
||||||
+ int i;
|
|
||||||
+ for (i = 0; i < num_msg; i++) {
|
|
||||||
+ const struct pam_message *msg = msgm[i];
|
|
||||||
+ if (msg == (const struct pam_message*)0)
|
|
||||||
+ continue;
|
|
||||||
+ if (msg->msg == (char*)0)
|
|
||||||
+ continue;
|
|
||||||
+ switch (msg->msg_style) {
|
|
||||||
+ case PAM_ERROR_MSG:
|
|
||||||
+ case PAM_TEXT_INFO:
|
|
||||||
+ initlog(L_VB, "pam_message %s", msg->msg);
|
|
||||||
+ default:
|
|
||||||
+ break;
|
|
||||||
+ }
|
|
||||||
+ }
|
|
||||||
+ return 0;
|
|
||||||
+}
|
|
||||||
+static const struct pam_conv conv = { null_conv, NULL };
|
|
||||||
+# define PAM_FAIL_CHECK(func, args...) \
|
|
||||||
+ { \
|
|
||||||
+ if ((pam_ret = (func)(args)) != PAM_SUCCESS) { \
|
|
||||||
+ initlog(L_VB, "%s", pam_strerror(pamh, pam_ret)); \
|
|
||||||
+ goto pam_error; \
|
|
||||||
+ } \
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+void notify_pam_dead_session(const char *id)
|
|
||||||
+{
|
|
||||||
+ struct utmp *oldut, ut;
|
|
||||||
+
|
|
||||||
+ setutent();
|
|
||||||
+
|
|
||||||
+ memset(&ut, 0, sizeof(ut));
|
|
||||||
+ ut.ut_type = DEAD_PROCESS;
|
|
||||||
+ strncpy(ut.ut_id, id, sizeof(ut.ut_id));
|
|
||||||
+
|
|
||||||
+ if ((oldut = getutid(&ut)) && (oldut->ut_type == USER_PROCESS)) {
|
|
||||||
+ int pam_ret;
|
|
||||||
+ char tty[UT_LINESIZE+ strlen(_PATH_DEV) + 1];
|
|
||||||
+
|
|
||||||
+ if (strncmp(oldut->ut_line, _PATH_DEV, strlen(_PATH_DEV)))
|
|
||||||
+ snprintf(tty, sizeof(tty), _PATH_DEV "%.*s",
|
|
||||||
+ UT_LINESIZE, oldut->ut_line);
|
|
||||||
+ else
|
|
||||||
+ snprintf(tty, sizeof(tty), "%.*s",
|
|
||||||
+ UT_LINESIZE, oldut->ut_line);
|
|
||||||
+
|
|
||||||
+ PAM_FAIL_CHECK(pam_start, "init", oldut->ut_user, &conv, &pamh);
|
|
||||||
+ PAM_FAIL_CHECK(pam_set_item, pamh, PAM_TTY, tty);
|
|
||||||
+ PAM_FAIL_CHECK(pam_set_item, pamh, PAM_RHOST, oldut->ut_host);
|
|
||||||
+ PAM_FAIL_CHECK(pam_close_session, pamh, PAM_SILENT);
|
|
||||||
+ pam_error:
|
|
||||||
+ pam_end(pamh, pam_ret);
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ endutent();
|
|
||||||
+}
|
|
||||||
+#endif /* USE_PAM && INIT_MAIN */
|
|
||||||
+
|
|
53
sysvinit-2.82-multiline.patch
Normal file
53
sysvinit-2.82-multiline.patch
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
--- contrib/start-stop-daemon.c
|
||||||
|
+++ contrib/start-stop-daemon.c
|
||||||
|
@@ -108,28 +108,28 @@
|
||||||
|
static void
|
||||||
|
do_help(void)
|
||||||
|
{
|
||||||
|
- printf("\
|
||||||
|
-start-stop-daemon for Debian Linux - small and fast C version written by\n\
|
||||||
|
-Marek Michalkiewicz <marekm@i17linuxb.ists.pwr.wroc.pl>, public domain.\n"
|
||||||
|
-VERSION "\n\
|
||||||
|
-\n\
|
||||||
|
-Usage:
|
||||||
|
- start-stop-daemon -S|--start options ... -- arguments ...\n\
|
||||||
|
- start-stop-daemon -K|--stop options ...\n\
|
||||||
|
- start-stop-daemon -H|--help\n\
|
||||||
|
- start-stop-daemon -V|--version\n\
|
||||||
|
-\n\
|
||||||
|
-Options (at least one of --exec|--pidfile|--user is required):
|
||||||
|
- -x|--exec <executable> program to start/check if it is running\n\
|
||||||
|
- -p|--pidfile <pid-file> pid file to check\n\
|
||||||
|
- -u|--user <username>|<uid> stop this user's processes\n\
|
||||||
|
- -n|--name <process-name> start/stop processes with this name\n\
|
||||||
|
- -s|--signal <signal> signal to send (default 15)\n\
|
||||||
|
- -t|--test test mode, don't do anything\n\
|
||||||
|
- -o|--oknodo exit status 0 (not 1) if nothing done\n\
|
||||||
|
- -q|--quiet | -v, --verbose\n\
|
||||||
|
-\n\
|
||||||
|
-Exit status: 0 = done 1 = nothing done (=> 0 if --oknodo) 2 = trouble\n");
|
||||||
|
+ printf(
|
||||||
|
+"start-stop-daemon for Debian Linux - small and fast C version written by\n"
|
||||||
|
+"Marek Michalkiewicz <marekm@i17linuxb.ists.pwr.wroc.pl>, public domain.\n"
|
||||||
|
+VERSION "\n"
|
||||||
|
+"\n"
|
||||||
|
+"Usage:\n"
|
||||||
|
+" start-stop-daemon -S|--start options ... -- arguments ...\n"
|
||||||
|
+" start-stop-daemon -K|--stop options ...\n"
|
||||||
|
+" start-stop-daemon -H|--help\n"
|
||||||
|
+" start-stop-daemon -V|--version\n"
|
||||||
|
+"\n"
|
||||||
|
+"Options (at least one of --exec|--pidfile|--user is required):\n"
|
||||||
|
+" -x|--exec <executable> program to start/check if it is running\n"
|
||||||
|
+" -p|--pidfile <pid-file> pid file to check\n"
|
||||||
|
+" -u|--user <username>|<uid> stop this user's processes\n"
|
||||||
|
+" -n|--name <process-name> start/stop processes with this name\n"
|
||||||
|
+" -s|--signal <signal> signal to send (default 15)\n"
|
||||||
|
+" -t|--test test mode, don't do anything\n"
|
||||||
|
+" -o|--oknodo exit status 0 (not 1) if nothing done\n"
|
||||||
|
+" -q|--quiet | -v, --verbose\n"
|
||||||
|
+"\n"
|
||||||
|
+"Exit status: 0 = done 1 = nothing done (=> 0 if --oknodo) 2 = trouble\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
26
sysvinit-2.85-paths.patch
Normal file
26
sysvinit-2.85-paths.patch
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
--- man/init.8
|
||||||
|
+++ man/init.8 2004-03-12 12:44:29.000000000 +0000
|
||||||
|
@@ -232,7 +232,7 @@ It activates the \fIkbrequest\fP action.
|
||||||
|
.SH CONFORMING TO
|
||||||
|
\fBInit\fP is compatible with the System V init. It works closely
|
||||||
|
together with the scripts in the directories
|
||||||
|
-\fI/etc/init.d\fP and \fI/etc/rc{runlevel}.d\fP.
|
||||||
|
+\fI/etc/init.d\fP and \fI/etc/init.d/rc{runlevel}.d\fP.
|
||||||
|
If your system uses this convention, there should be a \fIREADME\fP
|
||||||
|
file in the directory \fI/etc/init.d\fP explaining how these scripts work.
|
||||||
|
.\"}}}
|
||||||
|
--- src/paths.h
|
||||||
|
+++ src/paths.h 2004-03-12 12:45:00.000000000 +0000
|
||||||
|
@@ -26,10 +26,10 @@
|
||||||
|
#define SHELL "/bin/sh" /* Default shell */
|
||||||
|
#define SULOGIN "/sbin/sulogin" /* Sulogin */
|
||||||
|
#define INITSCRIPT "/etc/initscript" /* Initscript. */
|
||||||
|
-#define PWRSTAT "/etc/powerstatus" /* COMPAT: SIGPWR reason (OK/BAD) */
|
||||||
|
+#define PWRSTAT "/var/run/powerstatus" /* COMPAT: SIGPWR reason (OK/BAD) */
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
-#define INITLVL "/etc/initrunlvl" /* COMPAT: New runlevel */
|
||||||
|
+#define INITLVL "/var/run/initrunlvl" /* COMPAT: New runlevel */
|
||||||
|
#define INITLVL2 "/var/log/initrunlvl" /* COMPAT: New runlevel */
|
||||||
|
/* Note: INITLVL2 definition needs INITLVL */
|
||||||
|
#define HALTSCRIPT1 "/etc/init.d/halt" /* Called by "fast" shutdown */
|
@ -1,15 +1,6 @@
|
|||||||
--- man/init.8
|
--- man/init.8
|
||||||
+++ man/init.8 2010-03-19 14:44:16.000000000 +0000
|
+++ man/init.8 Fri Mar 12 12:26:35 2004
|
||||||
@@ -261,7 +261,7 @@ It activates the \fIkbrequest\fP action.
|
@@ -272,6 +272,7 @@
|
||||||
.SH CONFORMING TO
|
|
||||||
\fBInit\fP is compatible with the System V init. It works closely
|
|
||||||
together with the scripts in the directories
|
|
||||||
-\fI/etc/init.d\fP and \fI/etc/rc{runlevel}.d\fP.
|
|
||||||
+\fI/etc/init.d\fP and \fI/etc/init.d/rc{runlevel}.d\fP.
|
|
||||||
If your system uses this convention, there should be a \fIREADME\fP
|
|
||||||
file in the directory \fI/etc/init.d\fP explaining how these scripts work.
|
|
||||||
.\"}}}
|
|
||||||
@@ -301,6 +301,7 @@ page by Michael Haardt (u31b3hs@pool.inf
|
|
||||||
.\"}}}
|
.\"}}}
|
||||||
.\"{{{ See also
|
.\"{{{ See also
|
||||||
.SH "SEE ALSO"
|
.SH "SEE ALSO"
|
||||||
@ -18,8 +9,8 @@
|
|||||||
.BR login (1),
|
.BR login (1),
|
||||||
.BR sh (1),
|
.BR sh (1),
|
||||||
--- man/inittab.5
|
--- man/inittab.5
|
||||||
+++ man/inittab.5 2004-03-12 12:33:05.000000000 +0000
|
+++ man/inittab.5 Fri Mar 12 12:33:05 2004
|
||||||
@@ -197,7 +197,7 @@ rc::bootwait:/etc/rc
|
@@ -180,7 +180,7 @@
|
||||||
.fi
|
.fi
|
||||||
.sp
|
.sp
|
||||||
.RE
|
.RE
|
||||||
@ -28,7 +19,7 @@
|
|||||||
on tty1\-tty4.
|
on tty1\-tty4.
|
||||||
.PP
|
.PP
|
||||||
A more elaborate \fBinittab\fP with different runlevels (see the comments
|
A more elaborate \fBinittab\fP with different runlevels (see the comments
|
||||||
@@ -205,23 +205,20 @@ inside):
|
@@ -188,23 +188,20 @@
|
||||||
.RS
|
.RS
|
||||||
.sp
|
.sp
|
||||||
.nf
|
.nf
|
||||||
@ -61,7 +52,7 @@
|
|||||||
|
|
||||||
l0:0:wait:/etc/init.d/rc 0
|
l0:0:wait:/etc/init.d/rc 0
|
||||||
l1:1:wait:/etc/init.d/rc 1
|
l1:1:wait:/etc/init.d/rc 1
|
||||||
@@ -231,17 +228,27 @@ l4:4:wait:/etc/init.d/rc 4
|
@@ -214,17 +211,27 @@
|
||||||
l5:5:wait:/etc/init.d/rc 5
|
l5:5:wait:/etc/init.d/rc 5
|
||||||
l6:6:wait:/etc/init.d/rc 6
|
l6:6:wait:/etc/init.d/rc 6
|
||||||
|
|
||||||
@ -98,7 +89,7 @@
|
|||||||
|
|
||||||
.fi
|
.fi
|
||||||
.sp
|
.sp
|
||||||
@@ -261,5 +268,8 @@ by Michael Haardt (u31b3hs@pool.informat
|
@@ -244,5 +251,8 @@
|
||||||
.\"{{{ See also
|
.\"{{{ See also
|
||||||
.SH "SEE ALSO"
|
.SH "SEE ALSO"
|
||||||
.BR init (8),
|
.BR init (8),
|
||||||
@ -109,34 +100,32 @@
|
|||||||
+.BR mgetty (8)
|
+.BR mgetty (8)
|
||||||
.\"}}}
|
.\"}}}
|
||||||
--- man/killall5.8
|
--- man/killall5.8
|
||||||
+++ man/killall5.8 2010-03-19 14:43:25.000000000 +0000
|
+++ man/killall5.8 Fri Mar 12 12:26:35 2004
|
||||||
@@ -44,6 +44,7 @@ process were killed, and 1 if it was una
|
@@ -13,5 +13,6 @@
|
||||||
.SH SEE ALSO
|
.SH SEE ALSO
|
||||||
.BR halt (8),
|
.BR halt (8),
|
||||||
.BR reboot (8),
|
.BR reboot (8)
|
||||||
-.BR pidof (8)
|
|
||||||
+.BR pidof (8),
|
|
||||||
+.BR killproc (8)
|
+.BR killproc (8)
|
||||||
.SH AUTHOR
|
.SH AUTHOR
|
||||||
Miquel van Smoorenburg, miquels@cistron.nl
|
Miquel van Smoorenburg, miquels@cistron.nl
|
||||||
--- man/pidof.8
|
--- man/pidof.8
|
||||||
+++ man/pidof.8 2004-03-12 12:26:35.000000000 +0000
|
+++ man/pidof.8 Fri Mar 12 12:26:35 2004
|
||||||
@@ -83,6 +83,7 @@ that the executable name of running proc
|
@@ -40,6 +40,7 @@
|
||||||
so symbolic links to executables will also match.
|
that it returns pids of running programs that happen to have the same name
|
||||||
|
as the program you're after but are actually other programs.
|
||||||
.SH SEE ALSO
|
.SH SEE ALSO
|
||||||
+.BR pidofproc (8),
|
+.BR pidofproc (8),
|
||||||
.BR shutdown (8),
|
.BR shutdown (8),
|
||||||
.BR init (8),
|
.BR init (8),
|
||||||
.BR halt (8),
|
.BR halt (8),
|
||||||
--- man/sulogin.8
|
--- man/sulogin.8
|
||||||
+++ man/sulogin.8 2004-03-12 12:26:35.000000000 +0000
|
+++ man/sulogin.8 Fri Mar 12 12:26:35 2004
|
||||||
@@ -35,7 +35,7 @@ passes it the \fB\-b\fP option.
|
@@ -16,7 +16,7 @@
|
||||||
.PP
|
.PP
|
||||||
The user is prompted
|
The user is prompted
|
||||||
.IP "" .5i
|
.IP "" .5i
|
||||||
-Give root password for system maintenance
|
-Give root password for system maintenance
|
||||||
+Give root password for system login
|
+Give root password for system login
|
||||||
.br
|
.br
|
||||||
(or type Control\-D for normal startup):
|
(or type Control-D for normal startup):
|
||||||
.PP
|
.PP
|
164
sysvinit-2.86-full-time.patch
Normal file
164
sysvinit-2.86-full-time.patch
Normal file
@ -0,0 +1,164 @@
|
|||||||
|
man/last.1 | 6 ++++--
|
||||||
|
src/last.c | 43 ++++++++++++++++++++++++++++++++-----------
|
||||||
|
2 files changed, 36 insertions(+), 13 deletions(-)
|
||||||
|
|
||||||
|
Index: man/last.1
|
||||||
|
===================================================================
|
||||||
|
--- man/last.1 2005-12-05 18:05:40.000000000 +0100
|
||||||
|
+++ man/last.1 2005-12-05 18:09:27.000000000 +0100
|
||||||
|
@@ -12,7 +12,7 @@ last, lastb \- show listing of last logg
|
||||||
|
.RB [ \-R ]
|
||||||
|
.RB [ \-\fInum\fP ]
|
||||||
|
.RB "[ \-\fBn\fP \fInum\fP ]"
|
||||||
|
-.RB [ \-adiox ]
|
||||||
|
+.RB [ \-adFiox ]
|
||||||
|
.RB "[ \-\fBf\fP \fIfile\fP ]"
|
||||||
|
.RB "[ \-\fBt\fP \fIYYYYMMDDHHMMSS\fP ]"
|
||||||
|
.RI [ name... ]
|
||||||
|
@@ -23,7 +23,7 @@ last, lastb \- show listing of last logg
|
||||||
|
.RB [ \-\fInum\fP ]
|
||||||
|
.RB "[ \-\fBn\fP \fInum\fP ]"
|
||||||
|
.RB "[ \-\fBf\fP \fIfile\fP ]"
|
||||||
|
-.RB [ \-adiox ]
|
||||||
|
+.RB [ \-adFiox ]
|
||||||
|
.RI [ name... ]
|
||||||
|
.RI [ tty... ]
|
||||||
|
.\"}}}
|
||||||
|
@@ -69,6 +69,8 @@ with the next flag.
|
||||||
|
For non-local logins, Linux stores not only the host name of the remote
|
||||||
|
host but its IP number as well. This option translates the IP number
|
||||||
|
back into a hostname.
|
||||||
|
+.IP \fB\-F\fP
|
||||||
|
+Print full login and logout times and dates.
|
||||||
|
.IP \fB\-i\fP
|
||||||
|
This option is like \fB-d\fP in that it displays the IP number of the remote
|
||||||
|
host, but it displays the IP number in numbers-and-dots notation.
|
||||||
|
Index: src/last.c
|
||||||
|
===================================================================
|
||||||
|
--- src/last.c 2005-12-05 18:07:21.000000000 +0100
|
||||||
|
+++ src/last.c 2009-02-20 16:37:27.380797018 +0100
|
||||||
|
@@ -70,6 +70,7 @@ int showhost = 1; /* Show hostname too?
|
||||||
|
int altlist = 0; /* Show hostname at the end. */
|
||||||
|
int usedns = 0; /* Use DNS to lookup the hostname. */
|
||||||
|
int useip = 0; /* Print IP address in number format */
|
||||||
|
+int fulltime = 0; /* Print full dates and times */
|
||||||
|
int oldfmt = 0; /* Use old libc5 format? */
|
||||||
|
char **show = NULL; /* What do they want us to show */
|
||||||
|
char *ufile; /* Filename of this file */
|
||||||
|
@@ -388,9 +389,13 @@ int list(struct utmp *p, time_t t, int w
|
||||||
|
*/
|
||||||
|
tmp = (time_t)p->ut_time;
|
||||||
|
strcpy(logintime, ctime(&tmp));
|
||||||
|
- logintime[16] = 0;
|
||||||
|
- sprintf(logouttime, "- %s", ctime(&t) + 11);
|
||||||
|
- logouttime[7] = 0;
|
||||||
|
+ if (fulltime)
|
||||||
|
+ sprintf(logouttime, "- %s", ctime(&t));
|
||||||
|
+ else {
|
||||||
|
+ logintime[16] = 0;
|
||||||
|
+ sprintf(logouttime, "- %s", ctime(&t) + 11);
|
||||||
|
+ logouttime[7] = 0;
|
||||||
|
+ }
|
||||||
|
secs = t - p->ut_time;
|
||||||
|
mins = (secs / 60) % 60;
|
||||||
|
hours = (secs / 3600) % 24;
|
||||||
|
@@ -409,13 +414,21 @@ int list(struct utmp *p, time_t t, int w
|
||||||
|
break;
|
||||||
|
case R_NOW:
|
||||||
|
length[0] = 0;
|
||||||
|
- sprintf(logouttime, " still");
|
||||||
|
- sprintf(length, "logged in");
|
||||||
|
+ if (fulltime)
|
||||||
|
+ sprintf(logouttime, " still logged in");
|
||||||
|
+ else {
|
||||||
|
+ sprintf(logouttime, " still");
|
||||||
|
+ sprintf(length, "logged in");
|
||||||
|
+ }
|
||||||
|
break;
|
||||||
|
case R_PHANTOM:
|
||||||
|
length[0] = 0;
|
||||||
|
- sprintf(logouttime, " gone");
|
||||||
|
- sprintf(length, "- no logout");
|
||||||
|
+ if (fulltime)
|
||||||
|
+ sprintf(logouttime, " gone - no logout");
|
||||||
|
+ else {
|
||||||
|
+ sprintf(logouttime, " gone");
|
||||||
|
+ sprintf(length, "- no logout");
|
||||||
|
+ }
|
||||||
|
break;
|
||||||
|
case R_REBOOT:
|
||||||
|
logouttime[0] = 0; /* Print machine uptime */
|
||||||
|
@@ -450,23 +463,30 @@ int list(struct utmp *p, time_t t, int w
|
||||||
|
strcmp(s + 1, domainname) == 0) *s = 0;
|
||||||
|
#endif
|
||||||
|
if (!altlist) {
|
||||||
|
- snprintf(final, sizeof(final),
|
||||||
|
- "%-8.8s %-12.12s %-16.16s "
|
||||||
|
- "%-16.16s %-7.7s %-12.12s\n",
|
||||||
|
+ len = snprintf(final, sizeof(final),
|
||||||
|
+ fulltime ?
|
||||||
|
+ "%-8.8s %-12.12s %-16.16s %-24.24s %-26.26s %-12.12s\n" :
|
||||||
|
+ "%-8.8s %-12.12s %-16.16s %-16.16s %-7.7s %-12.12s\n",
|
||||||
|
p->ut_name, utline,
|
||||||
|
domain, logintime, logouttime, length);
|
||||||
|
} else {
|
||||||
|
- snprintf(final, sizeof(final),
|
||||||
|
+ len = snprintf(final, sizeof(final),
|
||||||
|
+ fulltime ?
|
||||||
|
+ "%-8.8s %-12.12s %-24.24s %-26.26s %-12.12s %s\n" :
|
||||||
|
"%-8.8s %-12.12s %-16.16s %-7.7s %-12.12s %s\n",
|
||||||
|
p->ut_name, utline,
|
||||||
|
logintime, logouttime, length, domain);
|
||||||
|
}
|
||||||
|
} else
|
||||||
|
- snprintf(final, sizeof(final),
|
||||||
|
+ len = snprintf(final, sizeof(final),
|
||||||
|
+ fulltime ?
|
||||||
|
+ "%-8.8s %-12.12s %-24.24s %-26.26s %-12.12s\n" :
|
||||||
|
"%-8.8s %-12.12s %-16.16s %-7.7s %-12.12s\n",
|
||||||
|
p->ut_name, utline,
|
||||||
|
logintime, logouttime, length);
|
||||||
|
|
||||||
|
+ final[sizeof(final)-1] = '\0';
|
||||||
|
+
|
||||||
|
/*
|
||||||
|
* Print out "final" string safely.
|
||||||
|
*/
|
||||||
|
@@ -477,6 +497,9 @@ int list(struct utmp *p, time_t t, int w
|
||||||
|
putchar('*');
|
||||||
|
}
|
||||||
|
|
||||||
|
+ if (len < 0 || len >= sizeof(final))
|
||||||
|
+ putchar('\n');
|
||||||
|
+
|
||||||
|
recsdone++;
|
||||||
|
if (maxrecs && recsdone >= maxrecs)
|
||||||
|
return 1;
|
||||||
|
@@ -492,7 +515,7 @@ void usage(char *s)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "Usage: %s [-num | -n num] [-f file] "
|
||||||
|
"[-t YYYYMMDDHHMMSS] "
|
||||||
|
- "[-R] [-a] [-d] [-i] [-o] [-x] "
|
||||||
|
+ "[-R] [-a] [-d] [-F] [-i] [-o] [-x] "
|
||||||
|
"[username..] [tty..]\n", s);
|
||||||
|
|
||||||
|
exit(1);
|
||||||
|
@@ -563,7 +586,7 @@ int main(int argc, char **argv)
|
||||||
|
progname = mybasename(argv[0]);
|
||||||
|
|
||||||
|
/* Process the arguments. */
|
||||||
|
- while((c = getopt(argc, argv, "f:n:Rxadiot:0123456789")) != EOF)
|
||||||
|
+ while((c = getopt(argc, argv, "f:n:RxadFiot:0123456789")) != EOF)
|
||||||
|
switch(c) {
|
||||||
|
case 'R':
|
||||||
|
showhost = 0;
|
||||||
|
@@ -594,6 +617,9 @@ int main(int argc, char **argv)
|
||||||
|
case 'a':
|
||||||
|
altlist++;
|
||||||
|
break;
|
||||||
|
+ case 'F':
|
||||||
|
+ fulltime++;
|
||||||
|
+ break;
|
||||||
|
case 't':
|
||||||
|
if ((until = parsetm(optarg)) == (time_t)-1) {
|
||||||
|
fprintf(stderr, "%s: Invalid time value \"%s\"\n",
|
90
sysvinit-2.86-fuse-no-kill.patch
Normal file
90
sysvinit-2.86-fuse-no-kill.patch
Normal file
@ -0,0 +1,90 @@
|
|||||||
|
--- src/killall5.c
|
||||||
|
+++ src/killall5.c 2009-01-27 15:32:40.000000000 +0000
|
||||||
|
@@ -59,6 +59,8 @@ typedef struct proc {
|
||||||
|
pid_t pid; /* Process ID. */
|
||||||
|
int sid; /* Session ID. */
|
||||||
|
char kernel; /* Kernel thread or zombie. */
|
||||||
|
+ char isfuse; /* Provides FUSE filesystems */
|
||||||
|
+ char isudev; /* Is the uevent handler */
|
||||||
|
char nfs; /* Binary is loacted on NFS part. */
|
||||||
|
struct proc *next; /* Pointer to next struct. */
|
||||||
|
} PROC;
|
||||||
|
@@ -410,6 +412,38 @@ int readarg(FILE *fp, char *buf, int sz)
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
+ * Scan the filedescriptors of pid for /dev/fuse
|
||||||
|
+ */
|
||||||
|
+int is_fuse(const char *pid) {
|
||||||
|
+ DIR *dir;
|
||||||
|
+ char path[256];
|
||||||
|
+ char buf[256];
|
||||||
|
+ struct dirent *d;
|
||||||
|
+ ssize_t len;
|
||||||
|
+
|
||||||
|
+ /* Open /proc/pid/fd/ */
|
||||||
|
+ snprintf(path, sizeof(path), "/proc/%s/fd", pid);
|
||||||
|
+ if ((dir = opendir(path)) != NULL) {
|
||||||
|
+ int dfd = dirfd(dir);
|
||||||
|
+ /* Walk through the directory. */
|
||||||
|
+ while ((d = readdir(dir)) != NULL) {
|
||||||
|
+ if (*d->d_name == '.')
|
||||||
|
+ continue;
|
||||||
|
+ /* check for /dev/fuse */
|
||||||
|
+ if ((len = readlinkat(dfd, d->d_name, buf, sizeof(buf))) > 0) {
|
||||||
|
+ buf[len] = '\0';
|
||||||
|
+ if (strcmp("/dev/fuse", buf) == 0)
|
||||||
|
+ return 1; /* Fuse filesystem */
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ closedir(dir);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ /* Not a fuse filesystem */
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
* Read the proc filesystem.
|
||||||
|
*/
|
||||||
|
int readproc()
|
||||||
|
@@ -565,13 +599,19 @@ int readproc()
|
||||||
|
|
||||||
|
/* Try to stat the executable. */
|
||||||
|
snprintf(path, sizeof(path), "/proc/%s/exe", d->d_name);
|
||||||
|
- if (check4nfs(path, NULL))
|
||||||
|
+ if (check4nfs(path, buf))
|
||||||
|
p->nfs = 1;
|
||||||
|
if ((p->nfs == 0) && (stat(path, &st) == 0)) {
|
||||||
|
p->dev = st.st_dev;
|
||||||
|
p->ino = st.st_ino;
|
||||||
|
}
|
||||||
|
|
||||||
|
+ /* Check for uevent handler */
|
||||||
|
+ p->isudev = (strncmp(buf, "/sbin/udevd", 11) == 0);
|
||||||
|
+
|
||||||
|
+ /* Check for provider of FUSE filesystems */
|
||||||
|
+ p->isfuse = is_fuse(d->d_name);
|
||||||
|
+
|
||||||
|
/* Link it into the list. */
|
||||||
|
p->next = plist;
|
||||||
|
plist = p;
|
||||||
|
@@ -907,14 +947,16 @@ int main(int argc, char **argv)
|
||||||
|
}
|
||||||
|
clear_mnt();
|
||||||
|
|
||||||
|
- /* Now kill all processes except our session. */
|
||||||
|
+ /* Now kill all processes except init (pid 1), our session, and FUSE filesystems. */
|
||||||
|
sid = (int)getsid(0);
|
||||||
|
pid = (int)getpid();
|
||||||
|
for (p = plist; p; p = p->next) {
|
||||||
|
- if (p->pid == 1 || p->pid == pid || p->sid == sid || p->kernel) {
|
||||||
|
+ if (p->pid == 1 || p->pid == pid || p->sid == sid || p->kernel || p->isfuse) {
|
||||||
|
kill(p->pid, SIGCONT);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
+ if (((sig == SIGTERM) || (sig == SIGKILL)) && p->isudev)
|
||||||
|
+ continue;
|
||||||
|
kill(p->pid, sig);
|
||||||
|
}
|
||||||
|
|
428
sysvinit-2.86-hddown.patch
Normal file
428
sysvinit-2.86-hddown.patch
Normal file
@ -0,0 +1,428 @@
|
|||||||
|
--- src/halt.c
|
||||||
|
+++ src/halt.c 2008-05-21 14:04:11.762054000 +0200
|
||||||
|
@@ -57,6 +57,7 @@ char *progname;
|
||||||
|
|
||||||
|
extern int ifdown(void);
|
||||||
|
extern int hddown(void);
|
||||||
|
+extern int hdflush(void);
|
||||||
|
extern void write_wtmp(char *user, char *id, int pid, int type, char *line);
|
||||||
|
|
||||||
|
/*
|
||||||
|
@@ -259,6 +260,8 @@ int main(int argc, char **argv)
|
||||||
|
|
||||||
|
if (do_hddown)
|
||||||
|
(void)hddown();
|
||||||
|
+ else
|
||||||
|
+ (void)hdflush();
|
||||||
|
|
||||||
|
if (do_nothing) exit(0);
|
||||||
|
|
||||||
|
--- src/hddown.c
|
||||||
|
+++ src/hddown.c 2008-05-21 14:48:40.913836000 +0200
|
||||||
|
@@ -5,6 +5,9 @@
|
||||||
|
*/
|
||||||
|
char *v_hddown = "@(#)hddown.c 1.02 22-Apr-2003 miquels@cistron.nl";
|
||||||
|
|
||||||
|
+#ifndef _GNU_SOURCE
|
||||||
|
+#define _GNU_SOURCE
|
||||||
|
+#endif
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
@@ -17,7 +20,371 @@ char *v_hddown = "@(#)hddown.c 1.02 22
|
||||||
|
|
||||||
|
#include <sys/ioctl.h>
|
||||||
|
#include <linux/hdreg.h>
|
||||||
|
+#include <linux/fs.h>
|
||||||
|
+
|
||||||
|
+#define USE_SYSFS
|
||||||
|
+#ifdef USE_SYSFS
|
||||||
|
+/*
|
||||||
|
+ * sysfs part Find all disks on the system, list out IDE and unmanaged
|
||||||
|
+ * SATA disks, flush the cache of those and shut them down.
|
||||||
|
+ * Author: Werner Fink <werner@suse.de>, 2007/06/12
|
||||||
|
+ *
|
||||||
|
+ */
|
||||||
|
+#include <limits.h>
|
||||||
|
+#include <errno.h>
|
||||||
|
+#include <sys/stat.h>
|
||||||
|
+#include <sys/types.h>
|
||||||
|
+#ifdef WORDS_BIGENDIAN
|
||||||
|
+#include <byteswap.h>
|
||||||
|
+#endif
|
||||||
|
+
|
||||||
|
+#define SYS_BLK "/sys/block"
|
||||||
|
+#define SYS_CLASS "/sys/class/scsi_disk"
|
||||||
|
+#define DEV_BASE "/dev"
|
||||||
|
+#define ISSPACE(c) (((c)==' ')||((c)=='\n')||((c)=='\t')||((c)=='\v')||((c)=='\r')||((c)=='\f'))
|
||||||
|
+
|
||||||
|
+/* Used in flush_cache_ext(), compare with <linux/hdreg.h> */
|
||||||
|
+#define IDBYTES 512
|
||||||
|
+#define MASK_EXT 0xE000 /* Bit 15 shall be zero, bit 14 shall be one, bit 13 flush cache ext */
|
||||||
|
+#define TEST_EXT 0x6000
|
||||||
|
+
|
||||||
|
+/* Maybe set in list_disks() and used in do_standby_idedisk() */
|
||||||
|
+#define DISK_IS_IDE 0x00000001
|
||||||
|
+#define DISK_IS_SATA 0x00000002
|
||||||
|
+#define DISK_EXTFLUSH 0x00000004
|
||||||
|
+#define DISK_REMOVABLE 0x00000008
|
||||||
|
+#define DISK_MANAGED 0x00000010
|
||||||
|
+#define DISK_NOSTANDBY 0x00000020
|
||||||
|
+#define DISK_FLUSHONLY DISK_NOSTANDBY
|
||||||
|
+
|
||||||
|
+static char *strstrip(char *str);
|
||||||
|
+static FILE *hdopen(const char* const format, const char* const name);
|
||||||
|
+static int flush_cache_ext(const char *device);
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Find all disks through /sys/block.
|
||||||
|
+ */
|
||||||
|
+static char *list_disks(DIR* blk, unsigned int* flags)
|
||||||
|
+{
|
||||||
|
+ struct dirent *d;
|
||||||
|
+
|
||||||
|
+ while ((d = readdir(blk))) {
|
||||||
|
+ (*flags) = 0;
|
||||||
|
+ if (d->d_name[1] == 'd' && (d->d_name[0] == 'h' || d->d_name[0] == 's')) {
|
||||||
|
+ char buf[NAME_MAX+1], lnk[NAME_MAX+1], *ptr;
|
||||||
|
+ FILE *fp;
|
||||||
|
+ int ret;
|
||||||
|
+
|
||||||
|
+ fp = hdopen(SYS_BLK "/%s/removable", d->d_name);
|
||||||
|
+ if ((long)fp <= 0) {
|
||||||
|
+ if ((long)fp < 0)
|
||||||
|
+ goto empty; /* error */
|
||||||
|
+ continue; /* no entry `removable' */
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ ret = getc(fp);
|
||||||
|
+ fclose(fp);
|
||||||
|
+
|
||||||
|
+ if (ret != '0')
|
||||||
|
+ (*flags) |= DISK_REMOVABLE;
|
||||||
|
+
|
||||||
|
+ if (d->d_name[0] == 'h') {
|
||||||
|
+ if ((*flags) & DISK_REMOVABLE)
|
||||||
|
+ continue; /* not a hard disk */
|
||||||
|
+
|
||||||
|
+ (*flags) |= DISK_IS_IDE;
|
||||||
|
+ if ((ret = flush_cache_ext(d->d_name))) {
|
||||||
|
+ if (ret < 0)
|
||||||
|
+ goto empty;
|
||||||
|
+ (*flags) |= DISK_EXTFLUSH;
|
||||||
|
+ }
|
||||||
|
+ break; /* old IDE disk not managed by kernel, out here */
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ ret = snprintf(buf, sizeof(buf), SYS_BLK "/%s/device", d->d_name);
|
||||||
|
+ if ((ret >= (int)sizeof(buf)) || (ret < 0))
|
||||||
|
+ goto empty; /* error */
|
||||||
|
+
|
||||||
|
+ ret = readlink(buf, lnk, sizeof(lnk));
|
||||||
|
+ if (ret >= (int)sizeof(lnk))
|
||||||
|
+ goto empty; /* error */
|
||||||
|
+ if (ret < 0) {
|
||||||
|
+ if (errno != ENOENT)
|
||||||
|
+ goto empty; /* error */
|
||||||
|
+ continue; /* no entry `device' */
|
||||||
|
+ }
|
||||||
|
+ lnk[ret] = '\0';
|
||||||
|
+
|
||||||
|
+ ptr = basename(lnk);
|
||||||
|
+ if (!ptr || !*ptr)
|
||||||
|
+ continue; /* should not happen */
|
||||||
|
+
|
||||||
|
+ fp = hdopen(SYS_CLASS "/%s/manage_start_stop", ptr);
|
||||||
|
+ if ((long)fp <= 0) {
|
||||||
|
+ if ((long)fp < 0)
|
||||||
|
+ goto empty; /* error */
|
||||||
|
+ } else {
|
||||||
|
+ ret = getc(fp);
|
||||||
|
+ fclose(fp);
|
||||||
|
+
|
||||||
|
+ if (ret != '0') {
|
||||||
|
+ (*flags) |= DISK_MANAGED;
|
||||||
|
+ continue;
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ fp = hdopen(SYS_BLK "/%s/device/vendor", d->d_name);
|
||||||
|
+ if ((long)fp <= 0) {
|
||||||
|
+ if ((long)fp < 0)
|
||||||
|
+ goto empty; /* error */
|
||||||
|
+ continue; /* no entry `device/vendor' */
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ ptr = fgets(buf, sizeof(buf), fp);
|
||||||
|
+ fclose(fp);
|
||||||
|
+ if (ptr == (char*)0)
|
||||||
|
+ continue; /* should not happen */
|
||||||
|
+
|
||||||
|
+ ptr = strstrip(buf);
|
||||||
|
+ if (*ptr == '\0')
|
||||||
|
+ continue; /* should not happen */
|
||||||
|
+
|
||||||
|
+ if (strncmp(buf, "ATA", sizeof(buf)) == 0) {
|
||||||
|
+ if ((*flags) & DISK_REMOVABLE)
|
||||||
|
+ continue; /* not a hard disk */
|
||||||
|
+
|
||||||
|
+ (*flags) |= (DISK_IS_IDE|DISK_IS_SATA);
|
||||||
|
+ if ((ret = flush_cache_ext(d->d_name))) {
|
||||||
|
+ if (ret < 0)
|
||||||
|
+ goto empty;
|
||||||
|
+ (*flags) |= DISK_EXTFLUSH;
|
||||||
|
+ }
|
||||||
|
+ break; /* new SATA disk to shutdown, out here */
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ if (((*flags) & DISK_REMOVABLE) == 0)
|
||||||
|
+ continue; /* Seems to be a real SCSI disk */
|
||||||
|
+
|
||||||
|
+ if ((ret = flush_cache_ext(d->d_name))) {
|
||||||
|
+ if (ret < 0)
|
||||||
|
+ goto empty;
|
||||||
|
+ (*flags) |= DISK_EXTFLUSH;
|
||||||
|
+ }
|
||||||
|
+ break; /* Removable disk like USB stick to shutdown */
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ if (d == (struct dirent*)0)
|
||||||
|
+ goto empty;
|
||||||
|
+ return d->d_name;
|
||||||
|
+empty:
|
||||||
|
+ return (char*)0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Put an disk in standby mode.
|
||||||
|
+ * Code stolen from hdparm.c
|
||||||
|
+ */
|
||||||
|
+static int do_standby_disk(char *device, unsigned int flags)
|
||||||
|
+{
|
||||||
|
+#ifndef WIN_STANDBYNOW1
|
||||||
|
+#define WIN_STANDBYNOW1 0xE0
|
||||||
|
+#endif
|
||||||
|
+#ifndef WIN_STANDBYNOW2
|
||||||
|
+#define WIN_STANDBYNOW2 0x94
|
||||||
|
+#endif
|
||||||
|
+#ifndef WIN_FLUSH_CACHE_EXT
|
||||||
|
+#define WIN_FLUSH_CACHE_EXT 0xEA
|
||||||
|
+#endif
|
||||||
|
+#ifndef WIN_FLUSH_CACHE
|
||||||
|
+#define WIN_FLUSH_CACHE 0xE7
|
||||||
|
+#endif
|
||||||
|
+ unsigned char flush1[4] = {WIN_FLUSH_CACHE_EXT,0,0,0};
|
||||||
|
+ unsigned char flush2[4] = {WIN_FLUSH_CACHE,0,0,0};
|
||||||
|
+ unsigned char stdby1[4] = {WIN_STANDBYNOW1,0,0,0};
|
||||||
|
+ unsigned char stdby2[4] = {WIN_STANDBYNOW2,0,0,0};
|
||||||
|
+ char buf[NAME_MAX+1];
|
||||||
|
+ int fd, ret;
|
||||||
|
+
|
||||||
|
+ ret = snprintf(buf, sizeof(buf), DEV_BASE "/%s", device);
|
||||||
|
+ if ((ret >= (int)sizeof(buf)) || (ret < 0))
|
||||||
|
+ return -1;
|
||||||
|
+
|
||||||
|
+ if ((fd = open(buf, O_RDWR|O_NONBLOCK)) < 0)
|
||||||
|
+ return -1;
|
||||||
|
|
||||||
|
+ switch (flags & DISK_EXTFLUSH) {
|
||||||
|
+ case DISK_EXTFLUSH:
|
||||||
|
+ if ((ret = ioctl(fd, HDIO_DRIVE_CMD, &flush1)) == 0)
|
||||||
|
+ break;
|
||||||
|
+ /* Extend flush rejected, try standard flush */
|
||||||
|
+ default:
|
||||||
|
+ ret = ioctl(fd, HDIO_DRIVE_CMD, &flush2) &&
|
||||||
|
+ ioctl(fd, BLKFLSBUF);
|
||||||
|
+ break;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ if ((flags & DISK_NOSTANDBY) == 0x0) {
|
||||||
|
+ ret = ioctl(fd, HDIO_DRIVE_CMD, &stdby1) &&
|
||||||
|
+ ioctl(fd, HDIO_DRIVE_CMD, &stdby2);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ close(fd);
|
||||||
|
+
|
||||||
|
+ if (ret)
|
||||||
|
+ return -1;
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * List all disks and put them in standby mode.
|
||||||
|
+ * This has the side-effect of flushing the writecache,
|
||||||
|
+ * which is exactly what we want on poweroff.
|
||||||
|
+ */
|
||||||
|
+int hddown(void)
|
||||||
|
+{
|
||||||
|
+ unsigned int flags;
|
||||||
|
+ char *disk;
|
||||||
|
+ DIR *blk;
|
||||||
|
+
|
||||||
|
+ if ((blk = opendir(SYS_BLK)) == (DIR*)0)
|
||||||
|
+ return -1;
|
||||||
|
+
|
||||||
|
+ while ((disk = list_disks(blk, &flags)))
|
||||||
|
+ do_standby_disk(disk, flags);
|
||||||
|
+
|
||||||
|
+ return closedir(blk);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * List all disks and cause them to flush their buffers.
|
||||||
|
+ */
|
||||||
|
+int hdflush(void)
|
||||||
|
+{
|
||||||
|
+ unsigned int flags;
|
||||||
|
+ char *disk;
|
||||||
|
+ DIR *blk;
|
||||||
|
+
|
||||||
|
+ if ((blk = opendir(SYS_BLK)) == (DIR*)0)
|
||||||
|
+ return -1;
|
||||||
|
+
|
||||||
|
+ while ((disk = list_disks(blk, &flags)))
|
||||||
|
+ do_standby_disk(disk, (flags|DISK_NOSTANDBY));
|
||||||
|
+
|
||||||
|
+ return closedir(blk);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Strip off trailing white spaces
|
||||||
|
+ */
|
||||||
|
+static char *strstrip(char *str)
|
||||||
|
+{
|
||||||
|
+ const size_t len = strlen(str);
|
||||||
|
+ if (len) {
|
||||||
|
+ char* end = str + len - 1;
|
||||||
|
+ while ((end != str) && ISSPACE(*end))
|
||||||
|
+ end--;
|
||||||
|
+ *(end + 1) = '\0'; /* remove trailing white spaces */
|
||||||
|
+ }
|
||||||
|
+ return str;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Open a sysfs file without getting a controlling tty
|
||||||
|
+ * and return FILE* pointer.
|
||||||
|
+ */
|
||||||
|
+static FILE *hdopen(const char* const format, const char* const name)
|
||||||
|
+{
|
||||||
|
+ char buf[NAME_MAX+1];
|
||||||
|
+ FILE *fp = (FILE*)-1;
|
||||||
|
+ int fd, ret;
|
||||||
|
+
|
||||||
|
+ ret = snprintf(buf, sizeof(buf), format, name);
|
||||||
|
+ if ((ret >= (int)sizeof(buf)) || (ret < 0))
|
||||||
|
+ goto error; /* error */
|
||||||
|
+
|
||||||
|
+ fd = open(buf, O_RDONLY|O_NOCTTY);
|
||||||
|
+ if (fd < 0) {
|
||||||
|
+ if (errno != ENOENT)
|
||||||
|
+ goto error; /* error */
|
||||||
|
+ fp = (FILE*)0;
|
||||||
|
+ goto error; /* no entry `removable' */
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ fp = fdopen(fd, "r");
|
||||||
|
+ if (fp == (FILE*)0)
|
||||||
|
+ close(fd); /* should not happen */
|
||||||
|
+error:
|
||||||
|
+ return fp;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Check IDE/(S)ATA hard disk identity for
|
||||||
|
+ * the FLUSH CACHE EXT bit set.
|
||||||
|
+ */
|
||||||
|
+static int flush_cache_ext(const char *device)
|
||||||
|
+{
|
||||||
|
+#ifndef WIN_IDENTIFY
|
||||||
|
+#define WIN_IDENTIFY 0xEC
|
||||||
|
+#endif
|
||||||
|
+ unsigned char args[4+IDBYTES];
|
||||||
|
+ unsigned short *id = (unsigned short*)(&args[4]);
|
||||||
|
+ char buf[NAME_MAX+1], *ptr;
|
||||||
|
+ int fd = -1, ret = 0;
|
||||||
|
+ FILE *fp;
|
||||||
|
+
|
||||||
|
+ fp = hdopen(SYS_BLK "/%s/size", device);
|
||||||
|
+ if ((long)fp <= 0) {
|
||||||
|
+ if ((long)fp < 0)
|
||||||
|
+ return -1; /* error */
|
||||||
|
+ goto out; /* no entry `size' */
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ ptr = fgets(buf, sizeof(buf), fp);
|
||||||
|
+ fclose(fp);
|
||||||
|
+ if (ptr == (char*)0)
|
||||||
|
+ goto out; /* should not happen */
|
||||||
|
+
|
||||||
|
+ ptr = strstrip(buf);
|
||||||
|
+ if (*ptr == '\0')
|
||||||
|
+ goto out; /* should not happen */
|
||||||
|
+
|
||||||
|
+ if ((size_t)atoll(buf) < (1<<28))
|
||||||
|
+ goto out; /* small disk */
|
||||||
|
+
|
||||||
|
+ ret = snprintf(buf, sizeof(buf), DEV_BASE "/%s", device);
|
||||||
|
+ if ((ret >= (int)sizeof(buf)) || (ret < 0))
|
||||||
|
+ return -1; /* error */
|
||||||
|
+
|
||||||
|
+ if ((fd = open(buf, O_RDONLY|O_NONBLOCK)) < 0)
|
||||||
|
+ goto out;
|
||||||
|
+
|
||||||
|
+ memset(&args[0], 0, sizeof(args));
|
||||||
|
+ args[0] = WIN_IDENTIFY;
|
||||||
|
+ args[3] = 1;
|
||||||
|
+ if (ioctl(fd, HDIO_DRIVE_CMD, &args))
|
||||||
|
+ goto out;
|
||||||
|
+#ifdef WORDS_BIGENDIAN
|
||||||
|
+# if 0
|
||||||
|
+ {
|
||||||
|
+ const unsigned short *end = id + IDBYTES/2;
|
||||||
|
+ const unsigned short *from = id;
|
||||||
|
+ unsigned short *to = id;
|
||||||
|
+
|
||||||
|
+ while (from < end)
|
||||||
|
+ *to++ = bswap_16(*from++);
|
||||||
|
+ }
|
||||||
|
+# else
|
||||||
|
+ id[83] = bswap_16(id[83]);
|
||||||
|
+# endif
|
||||||
|
+#endif
|
||||||
|
+ if ((id[83] & MASK_EXT) == TEST_EXT)
|
||||||
|
+ ret = 1;
|
||||||
|
+out:
|
||||||
|
+ if (fd >= 0)
|
||||||
|
+ close(fd);
|
||||||
|
+ return ret;
|
||||||
|
+}
|
||||||
|
+#else /* ! USE_SYSFS */
|
||||||
|
#define MAX_DISKS 64
|
||||||
|
#define PROC_IDE "/proc/ide"
|
||||||
|
#define DEV_BASE "/dev"
|
||||||
|
@@ -105,6 +472,12 @@ int hddown(void)
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
+int hdflush(void)
|
||||||
|
+{
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+#endif /* ! USE_SYSFS */
|
||||||
|
#else /* __linux__ */
|
||||||
|
|
||||||
|
int hddown(void)
|
||||||
|
@@ -112,6 +485,11 @@ int hddown(void)
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
+int hdflush(void)
|
||||||
|
+{
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
#endif /* __linux__ */
|
||||||
|
|
||||||
|
#ifdef STANDALONE
|
11
sysvinit-2.86-lib64.patch
Normal file
11
sysvinit-2.86-lib64.patch
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
--- src/Makefile
|
||||||
|
+++ src/Makefile 2005-10-19 12:03:39.000000000 +0200
|
||||||
|
@@ -50,7 +50,7 @@
|
||||||
|
MANDIR = /usr/share/man
|
||||||
|
|
||||||
|
# Additional libs for GNU libc.
|
||||||
|
-ifneq ($(wildcard /usr/lib/libcrypt.a),)
|
||||||
|
+ifneq ($(wildcard /usr/lib*/libcrypt.a),)
|
||||||
|
LCRYPT = -lcrypt
|
||||||
|
endif
|
||||||
|
|
40
sysvinit-2.86-mdmon-no-kill.patch
Normal file
40
sysvinit-2.86-mdmon-no-kill.patch
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
---
|
||||||
|
src/killall5.c | 10 ++++++++--
|
||||||
|
1 file changed, 8 insertions(+), 2 deletions(-)
|
||||||
|
|
||||||
|
--- src/killall5.c
|
||||||
|
+++ src/killall5.c
|
||||||
|
@@ -62,6 +62,7 @@ typedef struct proc {
|
||||||
|
char isfuse; /* Provides FUSE filesystems */
|
||||||
|
char isudev; /* Is the uevent handler */
|
||||||
|
char nfs; /* Binary is loacted on NFS part. */
|
||||||
|
+ char ismdmon; /* Is an instance of /sbin/mdmon. */
|
||||||
|
struct proc *next; /* Pointer to next struct. */
|
||||||
|
} PROC;
|
||||||
|
|
||||||
|
@@ -609,6 +610,9 @@ int readproc()
|
||||||
|
/* Check for uevent handler */
|
||||||
|
p->isudev = (strncmp(buf, "/sbin/udevd", 11) == 0);
|
||||||
|
|
||||||
|
+ /* Check for mdmon */
|
||||||
|
+ p->ismdmon = (strncmp(buf, "/sbin/mdmon", 11) == 0);
|
||||||
|
+
|
||||||
|
/* Check for provider of FUSE filesystems */
|
||||||
|
p->isfuse = is_fuse(d->d_name);
|
||||||
|
|
||||||
|
@@ -947,11 +951,13 @@ int main(int argc, char **argv)
|
||||||
|
}
|
||||||
|
clear_mnt();
|
||||||
|
|
||||||
|
- /* Now kill all processes except init (pid 1), our session, and FUSE filesystems. */
|
||||||
|
+ /* Now kill all processes except init (pid 1), our session,
|
||||||
|
+ * FUSE filesystems and /sbin/mdmon */
|
||||||
|
sid = (int)getsid(0);
|
||||||
|
pid = (int)getpid();
|
||||||
|
for (p = plist; p; p = p->next) {
|
||||||
|
- if (p->pid == 1 || p->pid == pid || p->sid == sid || p->kernel || p->isfuse) {
|
||||||
|
+ if (p->pid == 1 || p->pid == pid || p->sid == sid || p->kernel
|
||||||
|
+ || p->isfuse || p->ismdmon) {
|
||||||
|
kill(p->pid, SIGCONT);
|
||||||
|
continue;
|
||||||
|
}
|
480
sysvinit-2.86-nfs4pidof.patch
Normal file
480
sysvinit-2.86-nfs4pidof.patch
Normal file
@ -0,0 +1,480 @@
|
|||||||
|
--- src/killall5.c
|
||||||
|
+++ src/killall5.c 2009-03-27 11:42:17.780766281 +0100
|
||||||
|
@@ -40,6 +40,8 @@
|
||||||
|
#include <syslog.h>
|
||||||
|
#include <getopt.h>
|
||||||
|
#include <stdarg.h>
|
||||||
|
+#include <mntent.h>
|
||||||
|
+#include <sys/param.h>
|
||||||
|
|
||||||
|
char *Version = "@(#)killall5 2.86 31-Jul-2004 miquels@cistron.nl";
|
||||||
|
|
||||||
|
@@ -56,7 +58,8 @@ typedef struct proc {
|
||||||
|
dev_t dev; /* Device it is on */
|
||||||
|
pid_t pid; /* Process ID. */
|
||||||
|
int sid; /* Session ID. */
|
||||||
|
- int kernel; /* Kernel thread or zombie. */
|
||||||
|
+ char kernel; /* Kernel thread or zombie. */
|
||||||
|
+ char nfs; /* Binary is loacted on NFS part. */
|
||||||
|
struct proc *next; /* Pointer to next struct. */
|
||||||
|
} PROC;
|
||||||
|
|
||||||
|
@@ -73,9 +76,35 @@ typedef struct {
|
||||||
|
PIDQ *next;
|
||||||
|
} PIDQ_HEAD;
|
||||||
|
|
||||||
|
+typedef struct shadow
|
||||||
|
+{
|
||||||
|
+ struct shadow *next;
|
||||||
|
+ struct shadow *prev;
|
||||||
|
+ size_t nlen;
|
||||||
|
+ char * name;
|
||||||
|
+} SHADOW;
|
||||||
|
+
|
||||||
|
+typedef struct nfs
|
||||||
|
+{
|
||||||
|
+ struct nfs *next; /* Pointer to next struct. */
|
||||||
|
+ struct nfs *prev; /* Pointer to previous st. */
|
||||||
|
+ SHADOW *shadow; /* Pointer to shadows */
|
||||||
|
+ char * name;
|
||||||
|
+ size_t nlen;
|
||||||
|
+} NFS;
|
||||||
|
+#if !defined(__STDC_VERSION__) || (__STDC_VERSION__ < 199901L)
|
||||||
|
+# ifndef restrict
|
||||||
|
+# define restrict __restrict__
|
||||||
|
+# endif
|
||||||
|
+#endif
|
||||||
|
+#define alignof(type) ((sizeof(type)+(sizeof(void*)-1)) & ~(sizeof(void*)-1))
|
||||||
|
+
|
||||||
|
/* List of processes. */
|
||||||
|
PROC *plist;
|
||||||
|
|
||||||
|
+/* List of NFS mountes partitions. */
|
||||||
|
+NFS *nlist;
|
||||||
|
+
|
||||||
|
/* Did we stop all processes ? */
|
||||||
|
int sent_sigstop;
|
||||||
|
|
||||||
|
@@ -102,6 +131,18 @@ void *xmalloc(int bytes)
|
||||||
|
return p;
|
||||||
|
}
|
||||||
|
|
||||||
|
+#ifdef __GNUC__
|
||||||
|
+static inline void xmemalign(void **, size_t, size_t) __attribute__ ((nonnull (1)));
|
||||||
|
+#endif
|
||||||
|
+static inline void xmemalign(void **memptr, size_t alignment, size_t size)
|
||||||
|
+{
|
||||||
|
+ if ((posix_memalign(memptr, alignment, size)) < 0) {
|
||||||
|
+ if (sent_sigstop) kill(-1, SIGCONT);
|
||||||
|
+ nsyslog(LOG_ERR, "out of memory");
|
||||||
|
+ exit(1);
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/*
|
||||||
|
* See if the proc filesystem is there. Mount if needed.
|
||||||
|
*/
|
||||||
|
@@ -152,6 +193,211 @@ int mount_proc(void)
|
||||||
|
return did_mount;
|
||||||
|
}
|
||||||
|
|
||||||
|
+static inline int isnetfs(const char * type)
|
||||||
|
+{
|
||||||
|
+ static const char* netfs[] = {"nfs", "nfs4", "smbfs", "cifs", "afs", "ncpfs", (char*)0};
|
||||||
|
+ int n;
|
||||||
|
+ for (n = 0; netfs[n]; n++)
|
||||||
|
+ if (!strcasecmp(netfs[n], type))
|
||||||
|
+ return 1;
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Remember all NFS typed partitions.
|
||||||
|
+ */
|
||||||
|
+void init_nfs(void)
|
||||||
|
+{
|
||||||
|
+ struct stat st;
|
||||||
|
+ struct mntent * ent;
|
||||||
|
+ FILE * mnt;
|
||||||
|
+
|
||||||
|
+ nlist = (NFS*)0;
|
||||||
|
+
|
||||||
|
+ if (stat("/proc/version", &st) < 0)
|
||||||
|
+ return;
|
||||||
|
+ if ((mnt = setmntent("/proc/mounts", "r")) == (FILE*)0)
|
||||||
|
+ return;
|
||||||
|
+
|
||||||
|
+ while ((ent = getmntent(mnt))) {
|
||||||
|
+ if (isnetfs(ent->mnt_type)) {
|
||||||
|
+ size_t nlen = strlen(ent->mnt_dir);
|
||||||
|
+ NFS *restrict p;
|
||||||
|
+ xmemalign((void*)&p, sizeof(void*), alignof(NFS)+(nlen+1));
|
||||||
|
+ p->name = ((char*)p)+alignof(NFS);
|
||||||
|
+ p->nlen = nlen;
|
||||||
|
+ p->shadow = (SHADOW*)0;
|
||||||
|
+
|
||||||
|
+ strcpy(p->name, ent->mnt_dir);
|
||||||
|
+ if (nlist)
|
||||||
|
+ nlist->prev = p;
|
||||||
|
+ p->next = nlist;
|
||||||
|
+ p->prev = (NFS*)0;
|
||||||
|
+ nlist = p;
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ endmntent(mnt);
|
||||||
|
+
|
||||||
|
+ if ((mnt = setmntent("/proc/mounts", "r")) == (FILE*)0)
|
||||||
|
+ return;
|
||||||
|
+
|
||||||
|
+ while ((ent = getmntent(mnt))) {
|
||||||
|
+ NFS *p;
|
||||||
|
+
|
||||||
|
+ for (p = nlist; p; p = p->next) {
|
||||||
|
+ SHADOW * restrict s;
|
||||||
|
+ size_t nlen;
|
||||||
|
+
|
||||||
|
+ if (strcmp(ent->mnt_dir, p->name) == 0)
|
||||||
|
+ continue;
|
||||||
|
+ if (strncmp(ent->mnt_dir, p->name, p->nlen) != 0)
|
||||||
|
+ continue;
|
||||||
|
+
|
||||||
|
+ nlen = strlen(ent->mnt_dir);
|
||||||
|
+ xmemalign((void*)&s, sizeof(void*), alignof(SHADOW)+(nlen+1));
|
||||||
|
+ s->name = ((char*)s)+alignof(SHADOW);
|
||||||
|
+ s->nlen = nlen;
|
||||||
|
+
|
||||||
|
+ strcpy(s->name, ent->mnt_dir);
|
||||||
|
+ if (p->shadow)
|
||||||
|
+ p->shadow->prev = s;
|
||||||
|
+ s->next = p->shadow;
|
||||||
|
+ s->prev = (SHADOW*)0;
|
||||||
|
+ p->shadow = s;
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ endmntent(mnt);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+static void clear_shadow(SHADOW *restrict shadow)
|
||||||
|
+{
|
||||||
|
+ SHADOW *s, *n, *l;
|
||||||
|
+
|
||||||
|
+ n = shadow;
|
||||||
|
+ l = (SHADOW*)0;
|
||||||
|
+ for (s = shadow; n; s = n) {
|
||||||
|
+ l = s->prev;
|
||||||
|
+ n = s->next;
|
||||||
|
+ if (s == shadow) {
|
||||||
|
+ if (n) n->prev = (SHADOW*)0;
|
||||||
|
+ shadow = n;
|
||||||
|
+ } else if (l) {
|
||||||
|
+ if (n) n->prev = l;
|
||||||
|
+ l->next = n;
|
||||||
|
+ }
|
||||||
|
+ free(s);
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+static void clear_mnt(void)
|
||||||
|
+{
|
||||||
|
+ NFS *p, *n, *l;
|
||||||
|
+
|
||||||
|
+ n = nlist;
|
||||||
|
+ l = (NFS*)0;
|
||||||
|
+ for (p = nlist; n; p = n) {
|
||||||
|
+ l = p->prev;
|
||||||
|
+ n = p->next;
|
||||||
|
+ if (p == nlist) {
|
||||||
|
+ if (n) n->prev = (NFS*)0;
|
||||||
|
+ nlist = n;
|
||||||
|
+ } else if (l) {
|
||||||
|
+ if (n) n->prev = l;
|
||||||
|
+ l->next = n;
|
||||||
|
+ }
|
||||||
|
+ if (p->shadow)
|
||||||
|
+ clear_shadow(p->shadow);
|
||||||
|
+ free(p);
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Check if path is ia shadow off a NFS partition.
|
||||||
|
+ */
|
||||||
|
+static int shadow(SHADOW *restrict this, const char *restrict name, const size_t nlen)
|
||||||
|
+{
|
||||||
|
+ SHADOW *s;
|
||||||
|
+
|
||||||
|
+ if (!this)
|
||||||
|
+ goto out;
|
||||||
|
+ for (s = this; s; s = s->next) {
|
||||||
|
+ if (nlen < s->nlen)
|
||||||
|
+ continue;
|
||||||
|
+ if (name[s->nlen] != '\0' && name[s->nlen] != '/')
|
||||||
|
+ continue;
|
||||||
|
+ if (strncmp(name, s->name, s->nlen) == 0)
|
||||||
|
+ return 1;
|
||||||
|
+ }
|
||||||
|
+out:
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+/*
|
||||||
|
+ * Check path is located on a NFS partition.
|
||||||
|
+ */
|
||||||
|
+int check4nfs(const char * path, char * real)
|
||||||
|
+{
|
||||||
|
+ char buf[PATH_MAX+1];
|
||||||
|
+ const char *curr;
|
||||||
|
+ int deep = MAXSYMLINKS;
|
||||||
|
+
|
||||||
|
+ if (!nlist) return 0;
|
||||||
|
+
|
||||||
|
+ curr = path;
|
||||||
|
+ do {
|
||||||
|
+ const char *prev;
|
||||||
|
+ int len;
|
||||||
|
+
|
||||||
|
+ if ((prev = strdupa(curr)) == NULL) {
|
||||||
|
+ nsyslog(LOG_ERR, "strdupa(): %s\n", strerror(errno));
|
||||||
|
+ return 0;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ errno = 0;
|
||||||
|
+ if ((len = readlink(curr, buf, PATH_MAX)) < 0)
|
||||||
|
+ break;
|
||||||
|
+ buf[len] = '\0';
|
||||||
|
+
|
||||||
|
+ if (buf[0] != '/') {
|
||||||
|
+ const char *slash;
|
||||||
|
+
|
||||||
|
+ if ((slash = strrchr(prev, '/'))) {
|
||||||
|
+ size_t off = slash - prev + 1;
|
||||||
|
+
|
||||||
|
+ if (off + len > PATH_MAX)
|
||||||
|
+ len = PATH_MAX - off;
|
||||||
|
+
|
||||||
|
+ memmove(&buf[off], &buf[0], len + 1);
|
||||||
|
+ memcpy(&buf[0], prev, off);
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ curr = &buf[0];
|
||||||
|
+
|
||||||
|
+ if (deep-- <= 0) return 0;
|
||||||
|
+
|
||||||
|
+ } while (1);
|
||||||
|
+
|
||||||
|
+ if (real) strcpy(real, curr);
|
||||||
|
+
|
||||||
|
+ if (errno == EINVAL) {
|
||||||
|
+ const size_t nlen = strlen(curr);
|
||||||
|
+ NFS *p;
|
||||||
|
+ for (p = nlist; p; p = p->next) {
|
||||||
|
+ if (nlen < p->nlen)
|
||||||
|
+ continue;
|
||||||
|
+ if (curr[p->nlen] != '\0' && curr[p->nlen] != '/')
|
||||||
|
+ continue;
|
||||||
|
+ if (!strncmp(curr, p->name, p->nlen)) {
|
||||||
|
+ if (shadow(p->shadow, curr, nlen))
|
||||||
|
+ continue;
|
||||||
|
+ return 1;
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
int readarg(FILE *fp, char *buf, int sz)
|
||||||
|
{
|
||||||
|
int c = 0, f = 0;
|
||||||
|
@@ -173,8 +419,8 @@ int readproc()
|
||||||
|
PROC *p, *n;
|
||||||
|
struct dirent *d;
|
||||||
|
struct stat st;
|
||||||
|
- char path[256];
|
||||||
|
- char buf[256];
|
||||||
|
+ char path[PATH_MAX+1];
|
||||||
|
+ char buf[PATH_MAX+1];
|
||||||
|
char *s, *q;
|
||||||
|
unsigned long startcode, endcode;
|
||||||
|
int pid, f;
|
||||||
|
@@ -191,6 +437,7 @@ int readproc()
|
||||||
|
n = p->next;
|
||||||
|
if (p->argv0) free(p->argv0);
|
||||||
|
if (p->argv1) free(p->argv1);
|
||||||
|
+ if (p->statname) free(p->statname);
|
||||||
|
free(p);
|
||||||
|
}
|
||||||
|
plist = NULL;
|
||||||
|
@@ -225,6 +472,9 @@ int readproc()
|
||||||
|
nsyslog(LOG_ERR,
|
||||||
|
"can't get program name from %s\n",
|
||||||
|
path);
|
||||||
|
+ if (p->argv0) free(p->argv0);
|
||||||
|
+ if (p->argv1) free(p->argv1);
|
||||||
|
+ if (p->statname) free(p->statname);
|
||||||
|
free(p);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
@@ -248,6 +498,9 @@ int readproc()
|
||||||
|
p->sid = 0;
|
||||||
|
nsyslog(LOG_ERR, "can't read sid from %s\n",
|
||||||
|
path);
|
||||||
|
+ if (p->argv0) free(p->argv0);
|
||||||
|
+ if (p->argv1) free(p->argv1);
|
||||||
|
+ if (p->statname) free(p->statname);
|
||||||
|
free(p);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
@@ -256,6 +509,9 @@ int readproc()
|
||||||
|
fclose(fp);
|
||||||
|
} else {
|
||||||
|
/* Process disappeared.. */
|
||||||
|
+ if (p->argv0) free(p->argv0);
|
||||||
|
+ if (p->argv1) free(p->argv1);
|
||||||
|
+ if (p->statname) free(p->statname);
|
||||||
|
free(p);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
@@ -300,13 +556,18 @@ int readproc()
|
||||||
|
|
||||||
|
} else {
|
||||||
|
/* Process disappeared.. */
|
||||||
|
+ if (p->argv0) free(p->argv0);
|
||||||
|
+ if (p->argv1) free(p->argv1);
|
||||||
|
+ if (p->statname) free(p->statname);
|
||||||
|
free(p);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Try to stat the executable. */
|
||||||
|
snprintf(path, sizeof(path), "/proc/%s/exe", d->d_name);
|
||||||
|
- if (stat(path, &st) == 0) {
|
||||||
|
+ if (check4nfs(path, NULL))
|
||||||
|
+ p->nfs = 1;
|
||||||
|
+ if ((p->nfs == 0) && (stat(path, &st) == 0)) {
|
||||||
|
p->dev = st.st_dev;
|
||||||
|
p->ino = st.st_ino;
|
||||||
|
}
|
||||||
|
@@ -374,12 +635,25 @@ PIDQ_HEAD *pidof(char *prog)
|
||||||
|
PIDQ_HEAD *q;
|
||||||
|
struct stat st;
|
||||||
|
char *s;
|
||||||
|
+ int nfs = 0;
|
||||||
|
int dostat = 0;
|
||||||
|
int foundone = 0;
|
||||||
|
int ok = 0;
|
||||||
|
+ char real[PATH_MAX+1];
|
||||||
|
|
||||||
|
/* Try to stat the executable. */
|
||||||
|
- if (prog[0] == '/' && stat(prog, &st) == 0) dostat++;
|
||||||
|
+ if (prog[0] == '/') {
|
||||||
|
+ memset(&real[0], 0, sizeof(real));
|
||||||
|
+
|
||||||
|
+ if (check4nfs(prog, real))
|
||||||
|
+ nfs++; /* Binary located on NFS partition. */
|
||||||
|
+
|
||||||
|
+ if (real[0] != '\0')
|
||||||
|
+ prog = &real[0]; /* Binary or its symlink located on NFS. */
|
||||||
|
+
|
||||||
|
+ if ((nfs == 0) && (stat(prog, &st) == 0))
|
||||||
|
+ dostat++; /* Binary located on a local file system. */
|
||||||
|
+ }
|
||||||
|
|
||||||
|
/* Get basename of program. */
|
||||||
|
if ((s = strrchr(prog, '/')) == NULL)
|
||||||
|
@@ -393,10 +667,30 @@ PIDQ_HEAD *pidof(char *prog)
|
||||||
|
/* First try to find a match based on dev/ino pair. */
|
||||||
|
if (dostat) {
|
||||||
|
for (p = plist; p; p = p->next) {
|
||||||
|
- if (p->dev == st.st_dev && p->ino == st.st_ino) {
|
||||||
|
- add_pid_to_q(q, p);
|
||||||
|
- foundone++;
|
||||||
|
- }
|
||||||
|
+ if (p->nfs)
|
||||||
|
+ continue;
|
||||||
|
+ if (p->dev != st.st_dev || p->ino != st.st_ino)
|
||||||
|
+ continue;
|
||||||
|
+ add_pid_to_q(q, p);
|
||||||
|
+ foundone++;
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ /* Second try to find a match based on full path name on NFS located binaries */
|
||||||
|
+ if (!foundone && nfs) {
|
||||||
|
+ for (p = plist; p; p = p->next) {
|
||||||
|
+ char exe [PATH_MAX+1];
|
||||||
|
+ char path[PATH_MAX+1];
|
||||||
|
+ int len;
|
||||||
|
+
|
||||||
|
+ snprintf(exe, sizeof(exe), "/proc/%d/exe", p->pid);
|
||||||
|
+ if ((len = readlink(exe, path, PATH_MAX)) < 0)
|
||||||
|
+ continue;
|
||||||
|
+ path[len] = '\0';
|
||||||
|
+ if (strcmp(prog, path) != 0)
|
||||||
|
+ continue;
|
||||||
|
+ add_pid_to_q(q, p);
|
||||||
|
+ foundone++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -428,7 +722,7 @@ PIDQ_HEAD *pidof(char *prog)
|
||||||
|
if (ok) add_pid_to_q(q, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
- return q;
|
||||||
|
+ return q;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Give usage message and exit. */
|
||||||
|
@@ -477,6 +771,9 @@ int main_pidof(int argc, char **argv)
|
||||||
|
int first = 1;
|
||||||
|
int i, oind, opt, flags = 0;
|
||||||
|
|
||||||
|
+ /* Which NFS partitions are online? */
|
||||||
|
+ init_nfs();
|
||||||
|
+
|
||||||
|
for (oind = PIDOF_OMITSZ-1; oind > 0; oind--)
|
||||||
|
opid[oind] = 0;
|
||||||
|
opterr = 0;
|
||||||
|
@@ -561,6 +858,7 @@ int main(int argc, char **argv)
|
||||||
|
PROC *p;
|
||||||
|
int pid, sid = -1;
|
||||||
|
int sig = SIGKILL;
|
||||||
|
+ int did_mount;
|
||||||
|
|
||||||
|
/* Get program name. */
|
||||||
|
if ((progname = strrchr(argv[0], '/')) == NULL)
|
||||||
|
@@ -583,7 +881,10 @@ int main(int argc, char **argv)
|
||||||
|
}
|
||||||
|
|
||||||
|
/* First get the /proc filesystem online. */
|
||||||
|
- mount_proc();
|
||||||
|
+ did_mount = mount_proc();
|
||||||
|
+
|
||||||
|
+ /* Which NFS partitions are online? */
|
||||||
|
+ init_nfs();
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Ignoring SIGKILL and SIGSTOP do not make sense, but
|
||||||
|
@@ -604,13 +905,18 @@ int main(int argc, char **argv)
|
||||||
|
kill(-1, SIGCONT);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
+ clear_mnt();
|
||||||
|
|
||||||
|
/* Now kill all processes except our session. */
|
||||||
|
sid = (int)getsid(0);
|
||||||
|
pid = (int)getpid();
|
||||||
|
- for (p = plist; p; p = p->next)
|
||||||
|
- if (p->pid != pid && p->sid != sid && !p->kernel)
|
||||||
|
- kill(p->pid, sig);
|
||||||
|
+ for (p = plist; p; p = p->next) {
|
||||||
|
+ if (p->pid == 1 || p->pid == pid || p->sid == sid || p->kernel) {
|
||||||
|
+ kill(p->pid, SIGCONT);
|
||||||
|
+ continue;
|
||||||
|
+ }
|
||||||
|
+ kill(p->pid, sig);
|
||||||
|
+ }
|
||||||
|
|
||||||
|
/* And let them continue. */
|
||||||
|
kill(-1, SIGCONT);
|
33
sysvinit-2.86-race.patch
Normal file
33
sysvinit-2.86-race.patch
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
--- src/init.c
|
||||||
|
+++ src/init.c 2005-10-19 10:01:15.000000000 +0000
|
||||||
|
@@ -20,6 +20,14 @@
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
+/*
|
||||||
|
+ * 4 Sep 2001, Andrea Arcangeli:
|
||||||
|
+ * Fix a race in spawn() that is used to deadlock init in a
|
||||||
|
+ * waitpid() loop: must set the childhandler as default before forking
|
||||||
|
+ * off the child or the chld_handler could run before the waitpid loop
|
||||||
|
+ * has a chance to find its zombie-child.
|
||||||
|
+ */
|
||||||
|
+
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
|
#include <sys/ioctl.h>
|
||||||
|
@@ -976,6 +984,7 @@ int spawn(CHILD *ch, int *res)
|
||||||
|
dup(f);
|
||||||
|
dup(f);
|
||||||
|
}
|
||||||
|
+ SETSIG(sa, SIGCHLD, SIG_DFL, SA_RESTART);
|
||||||
|
if ((pid = fork()) < 0) {
|
||||||
|
initlog(L_VB, "cannot fork");
|
||||||
|
exit(1);
|
||||||
|
@@ -988,7 +997,6 @@ int spawn(CHILD *ch, int *res)
|
||||||
|
SETSIG(sa, SIGINT, SIG_IGN, SA_RESTART);
|
||||||
|
SETSIG(sa, SIGTSTP, SIG_IGN, SA_RESTART);
|
||||||
|
SETSIG(sa, SIGQUIT, SIG_IGN, SA_RESTART);
|
||||||
|
- SETSIG(sa, SIGCHLD, SIG_DFL, SA_RESTART);
|
||||||
|
|
||||||
|
while ((rc = waitpid(pid, &st, 0)) != pid)
|
||||||
|
if (rc < 0 && errno == ECHILD)
|
93
sysvinit-2.86-selinux.patch
Normal file
93
sysvinit-2.86-selinux.patch
Normal file
@ -0,0 +1,93 @@
|
|||||||
|
--- src/Makefile
|
||||||
|
+++ src/Makefile
|
||||||
|
@@ -57,7 +57,7 @@
|
||||||
|
all: $(BIN) $(SBIN) $(USRBIN)
|
||||||
|
|
||||||
|
init: init.o init_utmp.o
|
||||||
|
- $(CC) $(LDFLAGS) $(STATIC) -o $@ init.o init_utmp.o
|
||||||
|
+ $(CC) $(LDFLAGS) $(STATIC) -o $@ init.o init_utmp.o -lselinux -lsepol
|
||||||
|
|
||||||
|
halt: halt.o ifdown.o hddown.o utmp.o reboot.h
|
||||||
|
$(CC) $(LDFLAGS) -o $@ halt.o ifdown.o hddown.o utmp.o
|
||||||
|
@@ -78,7 +78,7 @@
|
||||||
|
$(CC) $(LDFLAGS) -o $@ runlevel.o
|
||||||
|
|
||||||
|
sulogin: sulogin.o
|
||||||
|
- $(CC) $(LDFLAGS) $(STATIC) -o $@ sulogin.o $(LCRYPT)
|
||||||
|
+ $(CC) $(LDFLAGS) $(STATIC) -o $@ sulogin.o $(LCRYPT) -lselinux
|
||||||
|
|
||||||
|
wall: dowall.o wall.o
|
||||||
|
$(CC) $(LDFLAGS) -o $@ dowall.o wall.o
|
||||||
|
--- src/init.c
|
||||||
|
+++ src/init.c
|
||||||
|
@@ -50,6 +50,8 @@
|
||||||
|
#include <stdarg.h>
|
||||||
|
#include <sys/syslog.h>
|
||||||
|
#include <sys/time.h>
|
||||||
|
+#include <selinux/selinux.h>
|
||||||
|
+#include <sepol/sepol.h>
|
||||||
|
|
||||||
|
#ifdef __i386__
|
||||||
|
# if (__GLIBC__ >= 2)
|
||||||
|
@@ -2643,6 +2645,7 @@
|
||||||
|
char *p;
|
||||||
|
int f;
|
||||||
|
int isinit;
|
||||||
|
+ int enforce = 0;
|
||||||
|
|
||||||
|
/* Get my own name */
|
||||||
|
if ((p = strrchr(argv[0], '/')) != NULL)
|
||||||
|
@@ -2706,6 +2709,20 @@
|
||||||
|
maxproclen += strlen(argv[f]) + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
+ if (getenv("SELINUX_INIT") == NULL && !is_selinux_enabled()) {
|
||||||
|
+ putenv("SELINUX_INIT=YES");
|
||||||
|
+ if (selinux_init_load_policy(&enforce) == 0 ) {
|
||||||
|
+ execv(myname, argv);
|
||||||
|
+ } else {
|
||||||
|
+ if (enforce > 0) {
|
||||||
|
+ /* SELinux in enforcing mode but load_policy failed */
|
||||||
|
+ /* At this point, we probably can't open /dev/console, so log() won't work */
|
||||||
|
+ printf("Unable to load SELinux Policy. Machine is in enforcing mode. Halting now.\n");
|
||||||
|
+ exit(1);
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
/* Start booting. */
|
||||||
|
argv0 = argv[0];
|
||||||
|
argv[1] = NULL;
|
||||||
|
--- src/sulogin.c
|
||||||
|
+++ src/sulogin.c
|
||||||
|
@@ -29,6 +29,8 @@
|
||||||
|
#if defined(__GLIBC__)
|
||||||
|
# include <crypt.h>
|
||||||
|
#endif
|
||||||
|
+#include <selinux/selinux.h>
|
||||||
|
+#include <selinux/get_context_list.h>
|
||||||
|
|
||||||
|
#define CHECK_DES 1
|
||||||
|
#define CHECK_MD5 1
|
||||||
|
@@ -374,6 +376,21 @@
|
||||||
|
signal(SIGINT, saved_sigint);
|
||||||
|
signal(SIGTSTP, saved_sigtstp);
|
||||||
|
signal(SIGQUIT, saved_sigquit);
|
||||||
|
+
|
||||||
|
+ if (is_selinux_enabled > 0) {
|
||||||
|
+ security_context_t scon=NULL;
|
||||||
|
+ char *seuser=NULL;
|
||||||
|
+ char *level=NULL;
|
||||||
|
+ if (getseuserbyname("root", &seuser, &level) == 0)
|
||||||
|
+ if (get_default_context_with_level(seuser, level, 0, &scon) > 0) {
|
||||||
|
+ if (setexeccon(scon) != 0)
|
||||||
|
+ fprintf(stderr, "setexeccon faile\n");
|
||||||
|
+ freecon(scon);
|
||||||
|
+ }
|
||||||
|
+ free(seuser);
|
||||||
|
+ free(level);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
execl(sushell, shell, NULL);
|
||||||
|
perror(sushell);
|
||||||
|
|
334
sysvinit-2.86-sulogin.patch
Normal file
334
sysvinit-2.86-sulogin.patch
Normal file
@ -0,0 +1,334 @@
|
|||||||
|
--- src/sulogin.c
|
||||||
|
+++ src/sulogin.c 2005-10-19 11:56:43.000000000 +0200
|
||||||
|
@@ -23,13 +23,16 @@
|
||||||
|
#include <pwd.h>
|
||||||
|
#include <shadow.h>
|
||||||
|
#include <termios.h>
|
||||||
|
+#include <sys/ttydefaults.h>
|
||||||
|
#include <sys/ioctl.h>
|
||||||
|
+#include <errno.h>
|
||||||
|
#if defined(__GLIBC__)
|
||||||
|
# include <crypt.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define CHECK_DES 1
|
||||||
|
#define CHECK_MD5 1
|
||||||
|
+#define FIXTTY 1
|
||||||
|
|
||||||
|
#define F_PASSWD "/etc/passwd"
|
||||||
|
#define F_SHADOW "/etc/shadow"
|
||||||
|
@@ -37,49 +40,80 @@
|
||||||
|
|
||||||
|
char *Version = "@(#)sulogin 2.85-3 23-Apr-2003 miquels@cistron.nl";
|
||||||
|
|
||||||
|
-int timeout = 0;
|
||||||
|
-int profile = 0;
|
||||||
|
+static int timeout;
|
||||||
|
+static int profile;
|
||||||
|
+
|
||||||
|
+static void (*saved_sigint) = SIG_DFL;
|
||||||
|
+static void (*saved_sigtstp) = SIG_DFL;
|
||||||
|
+static void (*saved_sigquit) = SIG_DFL;
|
||||||
|
|
||||||
|
#ifndef IUCLC
|
||||||
|
# define IUCLC 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
-#if 0
|
||||||
|
+#if FIXTTY
|
||||||
|
/*
|
||||||
|
* Fix the tty modes and set reasonable defaults.
|
||||||
|
* (I'm not sure if this is needed under Linux, but..)
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void fixtty(void)
|
||||||
|
{
|
||||||
|
struct termios tty;
|
||||||
|
+ int serial;
|
||||||
|
+
|
||||||
|
+ /* Skip serial console */
|
||||||
|
+ if (ioctl (0, TIOCMGET, (char*)&serial) == 0)
|
||||||
|
+ goto out;
|
||||||
|
+ /* Expected error */
|
||||||
|
+ serial = errno = 0;
|
||||||
|
|
||||||
|
tcgetattr(0, &tty);
|
||||||
|
|
||||||
|
- /*
|
||||||
|
- * Set or adjust tty modes.
|
||||||
|
- */
|
||||||
|
- tty.c_iflag &= ~(INLCR|IGNCR|IUCLC);
|
||||||
|
- tty.c_iflag |= ICRNL;
|
||||||
|
- tty.c_oflag &= ~(OCRNL|OLCUC|ONOCR|ONLRET|OFILL);
|
||||||
|
- tty.c_oflag |= OPOST|ONLCR;
|
||||||
|
- tty.c_cflag |= CLOCAL;
|
||||||
|
- tty.c_lflag = ISIG|ICANON|ECHO|ECHOE|ECHOK|ECHOCTL|ECHOKE;
|
||||||
|
-
|
||||||
|
- /*
|
||||||
|
- * Set the most important characters */
|
||||||
|
- */
|
||||||
|
- tty.c_cc[VINTR] = 3;
|
||||||
|
- tty.c_cc[VQUIT] = 28;
|
||||||
|
- tty.c_cc[VERASE] = 127;
|
||||||
|
- tty.c_cc[VKILL] = 24;
|
||||||
|
- tty.c_cc[VEOF] = 4;
|
||||||
|
- tty.c_cc[VTIME] = 0;
|
||||||
|
- tty.c_cc[VMIN] = 1;
|
||||||
|
- tty.c_cc[VSTART] = 17;
|
||||||
|
- tty.c_cc[VSTOP] = 19;
|
||||||
|
- tty.c_cc[VSUSP] = 26;
|
||||||
|
+ /* Use defaults of <sys/ttydefaults.h> for base settings */
|
||||||
|
+ tty.c_iflag |= TTYDEF_IFLAG;
|
||||||
|
+ tty.c_oflag |= TTYDEF_OFLAG;
|
||||||
|
+ tty.c_lflag |= TTYDEF_LFLAG;
|
||||||
|
+ tty.c_cflag |= (TTYDEF_SPEED | TTYDEF_CFLAG);
|
||||||
|
+
|
||||||
|
+ /* Sane setting, allow eight bit characters, no carriage return delay
|
||||||
|
+ * the same result as `stty sane cr0 pass8'
|
||||||
|
+ */
|
||||||
|
+ tty.c_iflag |= (BRKINT | ICRNL | IMAXBEL);
|
||||||
|
+ tty.c_iflag &= ~(IGNBRK | INLCR | IGNCR | IXOFF | IUCLC | IXANY | ISTRIP);
|
||||||
|
+ tty.c_oflag |= (OPOST | ONLCR | NL0 | CR0 | TAB0 | BS0 | VT0 | FF0);
|
||||||
|
+ tty.c_oflag &= ~(OLCUC | OCRNL | ONOCR | ONLRET | OFILL | OFDEL |\
|
||||||
|
+ NLDLY|CRDLY|TABDLY|BSDLY|VTDLY|FFDLY);
|
||||||
|
+ tty.c_lflag |= (ISIG | ICANON | IEXTEN | ECHO|ECHOE|ECHOK|ECHOCTL|ECHOKE);
|
||||||
|
+ tty.c_lflag &= ~(ECHONL | NOFLSH | XCASE | TOSTOP | ECHOPRT);
|
||||||
|
+ tty.c_cflag |= (CREAD | CS8 | B9600);
|
||||||
|
+ tty.c_cflag &= ~(PARENB);
|
||||||
|
+
|
||||||
|
+ /* VTIME and VMIN can overlap with VEOF and VEOL since they are
|
||||||
|
+ * only used for non-canonical mode. We just set the at the
|
||||||
|
+ * beginning, so nothing bad should happen.
|
||||||
|
+ */
|
||||||
|
+ tty.c_cc[VTIME] = 0;
|
||||||
|
+ tty.c_cc[VMIN] = 1;
|
||||||
|
+ tty.c_cc[VINTR] = CINTR;
|
||||||
|
+ tty.c_cc[VQUIT] = CQUIT;
|
||||||
|
+ tty.c_cc[VERASE] = CERASE; /* ASCII DEL (0177) */
|
||||||
|
+ tty.c_cc[VKILL] = CKILL;
|
||||||
|
+ tty.c_cc[VEOF] = CEOF;
|
||||||
|
+ tty.c_cc[VSWTC] = _POSIX_VDISABLE;
|
||||||
|
+ tty.c_cc[VSTART] = CSTART;
|
||||||
|
+ tty.c_cc[VSTOP] = CSTOP;
|
||||||
|
+ tty.c_cc[VSUSP] = CSUSP;
|
||||||
|
+ tty.c_cc[VEOL] = _POSIX_VDISABLE;
|
||||||
|
+ tty.c_cc[VREPRINT] = CREPRINT;
|
||||||
|
+ tty.c_cc[VDISCARD] = CDISCARD;
|
||||||
|
+ tty.c_cc[VWERASE] = CWERASE;
|
||||||
|
+ tty.c_cc[VLNEXT] = CLNEXT;
|
||||||
|
+ tty.c_cc[VEOL2] = _POSIX_VDISABLE;
|
||||||
|
|
||||||
|
tcsetattr(0, TCSANOW, &tty);
|
||||||
|
+out:
|
||||||
|
+ return;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
@@ -87,7 +121,8 @@
|
||||||
|
/*
|
||||||
|
* Called at timeout.
|
||||||
|
*/
|
||||||
|
-void alrm_handler()
|
||||||
|
+static
|
||||||
|
+void alrm_handler(int sig)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -96,6 +131,7 @@
|
||||||
|
* password is checked for traditional-style DES and
|
||||||
|
* FreeBSD-style MD5 encryption.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int valid(char *pass)
|
||||||
|
{
|
||||||
|
char *s;
|
||||||
|
@@ -134,6 +170,7 @@
|
||||||
|
/*
|
||||||
|
* Set a variable if the value is not NULL.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void set(char **var, char *val)
|
||||||
|
{
|
||||||
|
if (val) *var = val;
|
||||||
|
@@ -142,6 +179,7 @@
|
||||||
|
/*
|
||||||
|
* Get the root password entry.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
struct passwd *getrootpwent(int try_manually)
|
||||||
|
{
|
||||||
|
static struct passwd pwd;
|
||||||
|
@@ -244,6 +282,7 @@
|
||||||
|
* Ask for the password. Note that there is no
|
||||||
|
* default timeout as we normally skip this during boot.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
char *getpasswd(char *crypted)
|
||||||
|
{
|
||||||
|
struct sigaction sa;
|
||||||
|
@@ -252,11 +291,10 @@
|
||||||
|
char *ret = pass;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
- if (crypted[0])
|
||||||
|
- printf("Give root password for maintenance\n");
|
||||||
|
- else
|
||||||
|
- printf("Press enter for maintenance\n");
|
||||||
|
- printf("(or type Control-D to continue): ");
|
||||||
|
+ if (crypted[0]) {
|
||||||
|
+ printf("Give root password for login: ");
|
||||||
|
+ } else
|
||||||
|
+ printf("Press enter for login: ");
|
||||||
|
fflush(stdout);
|
||||||
|
|
||||||
|
tcgetattr(0, &old);
|
||||||
|
@@ -291,6 +329,7 @@
|
||||||
|
/*
|
||||||
|
* Password was OK, execute a shell.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void sushell(struct passwd *pwd)
|
||||||
|
{
|
||||||
|
char shell[128];
|
||||||
|
@@ -332,9 +371,9 @@
|
||||||
|
* Try to execute a shell.
|
||||||
|
*/
|
||||||
|
setenv("SHELL", sushell, 1);
|
||||||
|
- signal(SIGINT, SIG_DFL);
|
||||||
|
- signal(SIGTSTP, SIG_DFL);
|
||||||
|
- signal(SIGQUIT, SIG_DFL);
|
||||||
|
+ signal(SIGINT, saved_sigint);
|
||||||
|
+ signal(SIGTSTP, saved_sigtstp);
|
||||||
|
+ signal(SIGQUIT, saved_sigquit);
|
||||||
|
execl(sushell, shell, NULL);
|
||||||
|
perror(sushell);
|
||||||
|
|
||||||
|
@@ -343,6 +382,7 @@
|
||||||
|
perror(BINSH);
|
||||||
|
}
|
||||||
|
|
||||||
|
+static
|
||||||
|
void usage(void)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "Usage: sulogin [-e] [-p] [-t timeout] [tty device]\n");
|
||||||
|
@@ -385,50 +425,69 @@
|
||||||
|
/*
|
||||||
|
* See if we need to open an other tty device.
|
||||||
|
*/
|
||||||
|
- signal(SIGINT, SIG_IGN);
|
||||||
|
- signal(SIGQUIT, SIG_IGN);
|
||||||
|
- signal(SIGTSTP, SIG_IGN);
|
||||||
|
+ saved_sigint = signal(SIGINT, SIG_IGN);
|
||||||
|
+ saved_sigtstp = signal(SIGQUIT, SIG_IGN);
|
||||||
|
+ saved_sigquit = signal(SIGTSTP, SIG_IGN);
|
||||||
|
if (optind < argc) tty = argv[optind];
|
||||||
|
- if (tty) {
|
||||||
|
- if ((fd = open(tty, O_RDWR)) < 0) {
|
||||||
|
- perror(tty);
|
||||||
|
- } else if (!isatty(fd)) {
|
||||||
|
- fprintf(stderr, "%s: not a tty\n", tty);
|
||||||
|
- close(fd);
|
||||||
|
- } else {
|
||||||
|
-
|
||||||
|
- /*
|
||||||
|
- * Only go through this trouble if the new
|
||||||
|
- * tty doesn't fall in this process group.
|
||||||
|
- */
|
||||||
|
- pid = getpid();
|
||||||
|
- pgrp = getpgid(0);
|
||||||
|
- ppgrp = getpgid(getppid());
|
||||||
|
- ioctl(fd, TIOCGPGRP, &ttypgrp);
|
||||||
|
-
|
||||||
|
- if (pgrp != ttypgrp && ppgrp != ttypgrp) {
|
||||||
|
- if (pid != getsid(0)) {
|
||||||
|
- if (pid == getpgid(0))
|
||||||
|
- setpgid(0, getpgid(getppid()));
|
||||||
|
- setsid();
|
||||||
|
- }
|
||||||
|
|
||||||
|
- signal(SIGHUP, SIG_IGN);
|
||||||
|
+ if (!tty && !(tty = getenv("CONSOLE")))
|
||||||
|
+ tty = "/dev/console";
|
||||||
|
+
|
||||||
|
+ if ((fd = open(tty, O_RDWR)) < 0) {
|
||||||
|
+ perror(tty);
|
||||||
|
+ fd = dup(0);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ if (!isatty(fd)) {
|
||||||
|
+ fprintf(stderr, "%s: not a tty\n", tty);
|
||||||
|
+ close(fd);
|
||||||
|
+ } else {
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
+ * Only go through this trouble if the new
|
||||||
|
+ * tty doesn't fall in this process group.
|
||||||
|
+ */
|
||||||
|
+ pid = getpid();
|
||||||
|
+ pgrp = getpgid(0);
|
||||||
|
+ ppgrp = getpgid(getppid());
|
||||||
|
+ ttypgrp = tcgetpgrp(fd);
|
||||||
|
+
|
||||||
|
+ if (pgrp != ttypgrp && ppgrp != ttypgrp) {
|
||||||
|
+ if (pid != getsid(0)) {
|
||||||
|
+ if (pid == getpgid(0))
|
||||||
|
+ setpgid(0, getpgid(getppid()));
|
||||||
|
+ setsid();
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ signal(SIGHUP, SIG_IGN);
|
||||||
|
+ if (ttypgrp > 0)
|
||||||
|
ioctl(0, TIOCNOTTY, (char *)1);
|
||||||
|
- signal(SIGHUP, SIG_DFL);
|
||||||
|
- close(0);
|
||||||
|
- close(1);
|
||||||
|
- close(2);
|
||||||
|
+ signal(SIGHUP, SIG_DFL);
|
||||||
|
+ close(0);
|
||||||
|
+ close(1);
|
||||||
|
+ close(2);
|
||||||
|
+ if (fd > 2)
|
||||||
|
close(fd);
|
||||||
|
- fd = open(tty, O_RDWR);
|
||||||
|
+ if ((fd = open(tty, O_RDWR)) < 0) {
|
||||||
|
+ perror(tty);
|
||||||
|
+ } else {
|
||||||
|
+ tcsetpgrp(fd, ppgrp);
|
||||||
|
ioctl(0, TIOCSCTTY, (char *)1);
|
||||||
|
- dup(fd);
|
||||||
|
- dup(fd);
|
||||||
|
- } else
|
||||||
|
+ dup2(fd, 0);
|
||||||
|
+ dup2(fd, 1);
|
||||||
|
+ dup2(fd, 2);
|
||||||
|
+ if (fd > 2)
|
||||||
|
+ close(fd);
|
||||||
|
+ }
|
||||||
|
+ } else
|
||||||
|
+ if (fd > 2)
|
||||||
|
close(fd);
|
||||||
|
- }
|
||||||
|
}
|
||||||
|
|
||||||
|
+#if FIXTTY
|
||||||
|
+ fixtty();
|
||||||
|
+#endif
|
||||||
|
+
|
||||||
|
/*
|
||||||
|
* Get the root password.
|
||||||
|
*/
|
||||||
|
@@ -445,6 +504,9 @@
|
||||||
|
if (pwd->pw_passwd[0] == 0 ||
|
||||||
|
strcmp(crypt(p, pwd->pw_passwd), pwd->pw_passwd) == 0)
|
||||||
|
sushell(pwd);
|
||||||
|
+ saved_sigquit = signal(SIGQUIT, SIG_IGN);
|
||||||
|
+ saved_sigtstp = signal(SIGTSTP, SIG_IGN);
|
||||||
|
+ saved_sigint = signal(SIGINT, SIG_IGN);
|
||||||
|
printf("Login incorrect.\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -453,4 +515,3 @@
|
||||||
|
*/
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
-
|
18
sysvinit-2.86-usage-message.patch
Normal file
18
sysvinit-2.86-usage-message.patch
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
src/last.c | 4 +++-
|
||||||
|
1 files changed, 3 insertions(+), 1 deletion(-)
|
||||||
|
|
||||||
|
Index: src/last.c
|
||||||
|
===================================================================
|
||||||
|
--- src/last.c.orig 2005-12-05 18:05:40.000000000 +0100
|
||||||
|
+++ src/last.c 2005-12-05 18:07:21.000000000 +0100
|
||||||
|
@@ -492,7 +492,9 @@ void usage(char *s)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "Usage: %s [-num | -n num] [-f file] "
|
||||||
|
"[-t YYYYMMDDHHMMSS] "
|
||||||
|
- "[-R] [-x] [-o] [username..] [tty..]\n", s);
|
||||||
|
+ "[-R] [-a] [-d] [-i] [-o] [-x] "
|
||||||
|
+ "[username..] [tty..]\n", s);
|
||||||
|
+
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
203
sysvinit-2.86-utmp.patch
Normal file
203
sysvinit-2.86-utmp.patch
Normal file
@ -0,0 +1,203 @@
|
|||||||
|
--- src/init.c
|
||||||
|
+++ src/init.c 2006-08-22 13:04:27.000000000 +0000
|
||||||
|
@@ -107,6 +107,8 @@ sig_atomic_t got_signals; /* Set if we r
|
||||||
|
int emerg_shell = 0; /* Start emergency shell? */
|
||||||
|
int wrote_wtmp_reboot = 1; /* Set when we wrote the reboot record */
|
||||||
|
int wrote_utmp_reboot = 1; /* Set when we wrote the reboot record */
|
||||||
|
+int wrote_wtmp_rlevel = 1; /* Set when we wrote the runlevel record */
|
||||||
|
+int wrote_utmp_rlevel = 1; /* Set when we wrote the runlevel record */
|
||||||
|
int sltime = 5; /* Sleep time between TERM and KILL */
|
||||||
|
char *argv0; /* First arguments; show up in ps listing */
|
||||||
|
int maxproclen; /* Maximal length of argv[0] with \0 */
|
||||||
|
@@ -176,6 +178,8 @@ struct {
|
||||||
|
{ "-WU", D_WROTE_UTMP_REBOOT},
|
||||||
|
{ "-ST", D_SLTIME },
|
||||||
|
{ "-DB", D_DIDBOOT },
|
||||||
|
+ { "-LW", D_WROTE_WTMP_RLEVEL},
|
||||||
|
+ { "-LU", D_WROTE_UTMP_RLEVEL},
|
||||||
|
{ "", 0 }
|
||||||
|
};
|
||||||
|
struct {
|
||||||
|
@@ -371,6 +375,12 @@ static CHILD *get_record(FILE *f)
|
||||||
|
case D_DIDBOOT:
|
||||||
|
fscanf(f, "%d\n", &did_boot);
|
||||||
|
break;
|
||||||
|
+ case D_WROTE_WTMP_RLEVEL:
|
||||||
|
+ fscanf(f, "%d\n", &wrote_wtmp_rlevel);
|
||||||
|
+ break;
|
||||||
|
+ case D_WROTE_UTMP_RLEVEL:
|
||||||
|
+ fscanf(f, "%d\n", &wrote_utmp_rlevel);
|
||||||
|
+ break;
|
||||||
|
default:
|
||||||
|
if (cmd > 0 || cmd == C_EOF) {
|
||||||
|
oops_error = -1;
|
||||||
|
@@ -1697,6 +1707,8 @@ int read_level(int arg)
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Store both the old and the new runlevel. */
|
||||||
|
+ wrote_utmp_rlevel = 0;
|
||||||
|
+ wrote_wtmp_rlevel = 0;
|
||||||
|
write_utmp_wtmp("runlevel", "~~", foo + 256*runlevel, RUN_LVL, "~");
|
||||||
|
thislevel = foo;
|
||||||
|
prevlevel = runlevel;
|
||||||
|
@@ -1897,6 +1909,25 @@ void re_exec(void)
|
||||||
|
initlog(L_CO, "Attempt to re-exec failed");
|
||||||
|
}
|
||||||
|
|
||||||
|
+/*
|
||||||
|
+ * Redo utmp/wtmp entries if required or requested
|
||||||
|
+ * Check for written records and size of utmp
|
||||||
|
+ */
|
||||||
|
+static
|
||||||
|
+void redo_utmp_wtmp(void)
|
||||||
|
+{
|
||||||
|
+ struct stat ustat;
|
||||||
|
+ const int ret = stat(UTMP_FILE, &ustat);
|
||||||
|
+
|
||||||
|
+ if ((ret < 0) || (ustat.st_size == 0))
|
||||||
|
+ wrote_utmp_rlevel = wrote_utmp_reboot = 0;
|
||||||
|
+
|
||||||
|
+ if ((wrote_wtmp_reboot == 0) || (wrote_utmp_reboot == 0))
|
||||||
|
+ write_utmp_wtmp("reboot", "~~", 0, BOOT_TIME, "~");
|
||||||
|
+
|
||||||
|
+ if ((wrote_wtmp_rlevel == 0) || (wrote_wtmp_rlevel == 0))
|
||||||
|
+ write_utmp_wtmp("runlevel", "~~", thislevel + 256 * prevlevel, RUN_LVL, "~");
|
||||||
|
+}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* We got a change runlevel request through the
|
||||||
|
@@ -1928,6 +1959,7 @@ void fifo_new_level(int level)
|
||||||
|
if (oldlevel != 'S' && runlevel == 'S') console_stty();
|
||||||
|
if (runlevel == '6' || runlevel == '0' ||
|
||||||
|
runlevel == '1') console_stty();
|
||||||
|
+ if (runlevel > '1' && runlevel < '6') redo_utmp_wtmp();
|
||||||
|
read_inittab();
|
||||||
|
fail_cancel();
|
||||||
|
setproctitle("init [%c]", runlevel);
|
||||||
|
@@ -2223,6 +2255,8 @@ void boot_transitions()
|
||||||
|
}
|
||||||
|
if (loglevel > 0) {
|
||||||
|
initlog(L_VB, "Entering runlevel: %c", runlevel);
|
||||||
|
+ wrote_utmp_rlevel = 0;
|
||||||
|
+ wrote_wtmp_rlevel = 0;
|
||||||
|
write_utmp_wtmp("runlevel", "~~", runlevel + 256 * oldlevel, RUN_LVL, "~");
|
||||||
|
thislevel = runlevel;
|
||||||
|
prevlevel = oldlevel;
|
||||||
|
@@ -2401,6 +2435,7 @@ int init_main()
|
||||||
|
console_init();
|
||||||
|
|
||||||
|
if (!reload) {
|
||||||
|
+ int fd;
|
||||||
|
|
||||||
|
/* Close whatever files are open, and reset the console. */
|
||||||
|
close(0);
|
||||||
|
@@ -2418,7 +2453,8 @@ int init_main()
|
||||||
|
* Initialize /var/run/utmp (only works if /var is on
|
||||||
|
* root and mounted rw)
|
||||||
|
*/
|
||||||
|
- (void) close(open(UTMP_FILE, O_WRONLY|O_CREAT|O_TRUNC, 0644));
|
||||||
|
+ if ((fd = open(UTMP_FILE, O_WRONLY|O_CREAT|O_TRUNC, 0644)) >= 0)
|
||||||
|
+ close(fd);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Say hello to the world
|
||||||
|
--- src/init.h
|
||||||
|
+++ src/init.h 2006-08-22 12:29:39.000000000 +0000
|
||||||
|
@@ -99,6 +99,10 @@ typedef struct _child_ {
|
||||||
|
extern CHILD *family;
|
||||||
|
extern int wrote_wtmp_reboot;
|
||||||
|
extern int wrote_utmp_reboot;
|
||||||
|
+extern int wrote_wtmp_rlevel;
|
||||||
|
+extern int wrote_utmp_rlevel;
|
||||||
|
+extern char thislevel;
|
||||||
|
+extern char prevlevel;
|
||||||
|
|
||||||
|
/* Tokens in state parser */
|
||||||
|
#define C_VER 1
|
||||||
|
@@ -120,4 +124,6 @@ extern int wrote_utmp_reboot;
|
||||||
|
#define D_WROTE_UTMP_REBOOT -7
|
||||||
|
#define D_SLTIME -8
|
||||||
|
#define D_DIDBOOT -9
|
||||||
|
+#define D_WROTE_WTMP_RLEVEL -16
|
||||||
|
+#define D_WROTE_UTMP_RLEVEL -17
|
||||||
|
|
||||||
|
--- src/utmp.c
|
||||||
|
+++ src/utmp.c 2006-08-22 12:28:52.000000000 +0000
|
||||||
|
@@ -49,6 +49,12 @@ char *line) /* Which line is this */
|
||||||
|
struct utsname uname_buf;
|
||||||
|
|
||||||
|
/*
|
||||||
|
+ * Can't do much if WTMP_FILE is not present or not writable.
|
||||||
|
+ */
|
||||||
|
+ if (access(WTMP_FILE, W_OK) < 0)
|
||||||
|
+ return;
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
* Try to open the wtmp file. Note that we even try
|
||||||
|
* this if we have updwtmp() so we can see if the
|
||||||
|
* wtmp file is accessible.
|
||||||
|
@@ -69,6 +75,23 @@ char *line) /* Which line is this */
|
||||||
|
*/
|
||||||
|
if (wrote_wtmp_reboot == 0 && type != BOOT_TIME)
|
||||||
|
write_wtmp("reboot", "~~", 0, BOOT_TIME, "~");
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
+ * Note if we are going to write a runlevel record.
|
||||||
|
+ */
|
||||||
|
+ if (type == RUN_LVL) wrote_wtmp_rlevel++;
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
+ * See if we need to write a runlevel record. The reason that
|
||||||
|
+ * we are being so paranoid is that when we first tried to
|
||||||
|
+ * write the reboot record, /var was possibly not mounted
|
||||||
|
+ * yet. As soon as we can open WTMP we write a delayed runlevel record.
|
||||||
|
+ */
|
||||||
|
+ if (wrote_wtmp_rlevel == 0 && type != RUN_LVL) {
|
||||||
|
+ int runlevel = thislevel;
|
||||||
|
+ int oldlevel = prevlevel;
|
||||||
|
+ write_wtmp("runlevel", "~~", runlevel + 256 * oldlevel, RUN_LVL, "~");
|
||||||
|
+ }
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
@@ -115,9 +138,9 @@ char *oldline) /* Line of old utmp ent
|
||||||
|
struct utmp *utmptr;
|
||||||
|
|
||||||
|
/*
|
||||||
|
- * Can't do much if UTMP_FILE is not present.
|
||||||
|
+ * Can't do much if UTMP_FILE is not present or not writable.
|
||||||
|
*/
|
||||||
|
- if (access(UTMP_FILE, F_OK) < 0)
|
||||||
|
+ if (access(UTMP_FILE, W_OK) < 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
#ifdef INIT_MAIN
|
||||||
|
@@ -130,10 +153,27 @@ char *oldline) /* Line of old utmp ent
|
||||||
|
* See if we need to write a reboot record. The reason that
|
||||||
|
* we are being so paranoid is that when we first tried to
|
||||||
|
* write the reboot record, /var was possibly not mounted
|
||||||
|
- * yet. As soon as we can open WTMP we write a delayed boot record.
|
||||||
|
+ * yet. As soon as we can open UTMP we write a delayed boot record.
|
||||||
|
*/
|
||||||
|
if (wrote_utmp_reboot == 0 && type != BOOT_TIME)
|
||||||
|
write_utmp("reboot", "~~", 0, BOOT_TIME, "~", NULL);
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
+ * Note if we are going to write a runlevel record.
|
||||||
|
+ */
|
||||||
|
+ if (type == RUN_LVL) wrote_utmp_rlevel++;
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
+ * See if we need to write a runlevel record. The reason that
|
||||||
|
+ * we are being so paranoid is that when we first tried to
|
||||||
|
+ * write the reboot record, /var was possibly not mounted
|
||||||
|
+ * yet. As soon as we can open UTMP we write a delayed runlevel record.
|
||||||
|
+ */
|
||||||
|
+ if (wrote_utmp_rlevel == 0 && type != RUN_LVL) {
|
||||||
|
+ int runlevel = thislevel;
|
||||||
|
+ int oldlevel = prevlevel;
|
||||||
|
+ write_utmp("runlevel", "~~", runlevel + 256 * oldlevel, RUN_LVL, "~", NULL);
|
||||||
|
+ }
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*
|
970
sysvinit-2.86.dif
Normal file
970
sysvinit-2.86.dif
Normal file
@ -0,0 +1,970 @@
|
|||||||
|
--- .pkgextract
|
||||||
|
+++ .pkgextract 2006-08-18 14:45:28.000000000 +0200
|
||||||
|
@@ -0,0 +1,15 @@
|
||||||
|
+patch -p0 -b -s --suffix=.nfs4pidof < ../sysvinit-2.86-nfs4pidof.patch
|
||||||
|
+patch -p0 -b -s --suffix=.sulogin < ../sysvinit-2.86-sulogin.patch
|
||||||
|
+patch -p0 -b -s --suffix=.ststdmn < ../sysvinit-2.82-startstop.patch
|
||||||
|
+patch -p0 -b -s --suffix=.suse < ../sysvinit-2.85-suse.patch
|
||||||
|
+patch -p0 -b -s --suffix=.paths < ../sysvinit-2.85-paths.patch
|
||||||
|
+patch -p0 -b -s --suffix=.utmp < ../sysvinit-2.86-utmp.patch
|
||||||
|
+patch -p0 -b -s --suffix=.race < ../sysvinit-2.86-race.patch
|
||||||
|
+patch -p0 -b -s --suffix=.lib64 < ../sysvinit-2.86-lib64.patch
|
||||||
|
+patch -p0 -b -s --suffix=.mltline < ../sysvinit-2.82-multiline.patch
|
||||||
|
+patch -p0 -b -s --suffix=.usage < ../sysvinit-2.86-usage-message.patch
|
||||||
|
+patch -p0 -b -s --suffix=.fulltime < ../sysvinit-2.86-full-time.patch
|
||||||
|
+patch -p0 -b -s --suffix=.hddown < ../sysvinit-2.86-hddown.patch
|
||||||
|
+patch -p0 -b -s --suffix=.selinux < ../sysvinit-2.86-selinux.patch
|
||||||
|
+patch -p0 -b -s --suffix=.fuse < ../sysvinit-2.86-fuse-no-kill.patch
|
||||||
|
+patch -p0 -b -s --suffix=.mdmon < ../sysvinit-2.86-mdmon-no-kill.patch
|
||||||
|
--- src/Makefile
|
||||||
|
+++ src/Makefile 2009-05-11 10:05:28.482401539 +0200
|
||||||
|
@@ -8,17 +8,20 @@
|
||||||
|
# Version: @(#)Makefile 2.85-13 23-Mar-2004 miquels@cistron.nl
|
||||||
|
#
|
||||||
|
|
||||||
|
+DISTRO = SuSE
|
||||||
|
+
|
||||||
|
CC = gcc
|
||||||
|
-CFLAGS = -Wall -O2 -fomit-frame-pointer -D_GNU_SOURCE
|
||||||
|
-LDFLAGS = -s
|
||||||
|
-STATIC =
|
||||||
|
+CFLAGS = -Wall $(RPM_OPT_FLAGS) -D_GNU_SOURCE -pipe
|
||||||
|
+LDFLAGS = -Wl,-warn-common,--as-needed,-O2
|
||||||
|
+STATIC = -Wl,--reduce-memory-overheads,--hash-size=8599
|
||||||
|
+IFLAGS = -D__NO_STRING_INLINES -D__OPTIMIZE_SIZE__ -Os
|
||||||
|
|
||||||
|
# For some known distributions we do not build all programs, otherwise we do.
|
||||||
|
BIN =
|
||||||
|
SBIN = init halt shutdown runlevel killall5
|
||||||
|
-USRBIN = last mesg
|
||||||
|
+USRBIN = last
|
||||||
|
|
||||||
|
-MAN1 = last.1 lastb.1 mesg.1
|
||||||
|
+MAN1 = last.1 lastb.1
|
||||||
|
MAN5 = initscript.5 inittab.5
|
||||||
|
MAN8 = halt.8 init.8 killall5.8 pidof.8 poweroff.8 reboot.8 runlevel.8
|
||||||
|
MAN8 += shutdown.8 telinit.8
|
||||||
|
@@ -26,27 +29,36 @@ MAN8 += shutdown.8 telinit.8
|
||||||
|
ifeq ($(DISTRO),)
|
||||||
|
BIN += mountpoint
|
||||||
|
SBIN += sulogin bootlogd
|
||||||
|
-USRBIN += utmpdump wall
|
||||||
|
-MAN1 += mountpoint.1 wall.1
|
||||||
|
+USRBIN += utmpdump wall mesg
|
||||||
|
+MAN1 += utmpdump.1 mountpoint.1 wall.1 mesg.1
|
||||||
|
MAN8 += sulogin.8 bootlogd.8
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(DISTRO),Debian)
|
||||||
|
BIN += mountpoint
|
||||||
|
SBIN += sulogin bootlogd
|
||||||
|
-MAN1 += mountpoint.1
|
||||||
|
+USRBIN += mesg
|
||||||
|
+MAN1 += mountpoint.1 mesg.1
|
||||||
|
MAN8 += sulogin.8 bootlogd.8
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(DISTRO),Owl)
|
||||||
|
-USRBIN += wall
|
||||||
|
-MAN1 += wall.1
|
||||||
|
+USRBIN += wall mesg
|
||||||
|
+MAN1 += wall.1 mesg.1
|
||||||
|
+endif
|
||||||
|
+
|
||||||
|
+ifeq ($(DISTRO),SuSE)
|
||||||
|
+BIN += mountpoint
|
||||||
|
+SBIN += sulogin
|
||||||
|
+USRBIN += utmpdump
|
||||||
|
+MAN1 += utmpdump.1 mountpoint.1
|
||||||
|
+MAN8 += sulogin.8
|
||||||
|
endif
|
||||||
|
|
||||||
|
BIN_OWNER = root
|
||||||
|
BIN_GROUP = root
|
||||||
|
BIN_COMBO = $(BIN_OWNER):$(BIN_GROUP)
|
||||||
|
-INSTALL = install -o $(BIN_OWNER) -g $(BIN_GROUP)
|
||||||
|
+INSTALL = install
|
||||||
|
MANDIR = /usr/share/man
|
||||||
|
|
||||||
|
# Additional libs for GNU libc.
|
||||||
|
@@ -90,13 +102,13 @@ bootlogd: bootlogd.o
|
||||||
|
$(CC) $(LDFLAGS) -o $@ bootlogd.o -lutil
|
||||||
|
|
||||||
|
init.o: init.c init.h set.h reboot.h initreq.h
|
||||||
|
- $(CC) -c $(CFLAGS) init.c
|
||||||
|
+ $(CC) -c $(CFLAGS) $(IFLAGS) init.c
|
||||||
|
|
||||||
|
utmp.o: utmp.c init.h
|
||||||
|
$(CC) -c $(CFLAGS) utmp.c
|
||||||
|
|
||||||
|
init_utmp.o: utmp.c init.h
|
||||||
|
- $(CC) -c $(CFLAGS) -DINIT_MAIN utmp.c -o init_utmp.o
|
||||||
|
+ $(CC) -c $(CFLAGS) -DINIT_MAIN $(IFLAGS) utmp.c -o init_utmp.o
|
||||||
|
|
||||||
|
cleanobjs:
|
||||||
|
rm -f *.o *.bak
|
||||||
|
@@ -119,10 +131,10 @@ install:
|
||||||
|
for i in $(USRBIN); do \
|
||||||
|
$(INSTALL) -m 755 $$i $(ROOT)/usr/bin/; \
|
||||||
|
done
|
||||||
|
- # $(INSTALL) -m 755 etc/initscript.sample $(ROOT)/etc/
|
||||||
|
- ln -sf halt $(ROOT)/sbin/reboot
|
||||||
|
- ln -sf halt $(ROOT)/sbin/poweroff
|
||||||
|
- ln -sf init $(ROOT)/sbin/telinit
|
||||||
|
+ ln -sf halt $(ROOT)/sbin/reboot
|
||||||
|
+ ln -sf halt $(ROOT)/sbin/poweroff
|
||||||
|
+ ln -sf init $(ROOT)/sbin/telinit
|
||||||
|
+ ln -sf killall5 $(ROOT)/sbin/pidof
|
||||||
|
ln -sf ../sbin/killall5 $(ROOT)/bin/pidof
|
||||||
|
if [ ! -f $(ROOT)/usr/bin/lastb ]; then \
|
||||||
|
ln -sf last $(ROOT)/usr/bin/lastb; \
|
||||||
|
--- src/bootlogd.c
|
||||||
|
+++ src/bootlogd.c 2006-08-18 14:45:28.000000000 +0200
|
||||||
|
@@ -210,7 +210,7 @@ int isconsole(char *s, char *res, int rl
|
||||||
|
int consolename(char *res, int rlen)
|
||||||
|
{
|
||||||
|
#ifdef TIOCGDEV
|
||||||
|
- unsigned int kdev;
|
||||||
|
+ kdev_t kdev;
|
||||||
|
#endif
|
||||||
|
struct stat st, st2;
|
||||||
|
char buf[256];
|
||||||
|
@@ -506,7 +506,7 @@ int main(int argc, char **argv)
|
||||||
|
}
|
||||||
|
|
||||||
|
(void)ioctl(0, TIOCCONS, NULL);
|
||||||
|
-#if 1
|
||||||
|
+#if 0
|
||||||
|
/* Work around bug in 2.1/2.2 kernels. Fixed in 2.2.13 and 2.3.18 */
|
||||||
|
if ((n = open("/dev/tty0", O_RDWR)) >= 0) {
|
||||||
|
(void)ioctl(n, TIOCCONS, NULL);
|
||||||
|
--- src/dowall.c
|
||||||
|
+++ src/dowall.c 2006-08-18 14:45:28.000000000 +0200
|
||||||
|
@@ -65,7 +65,7 @@ static void getuidtty(char **userp, char
|
||||||
|
uid_t uid;
|
||||||
|
char *tty;
|
||||||
|
static char uidbuf[32];
|
||||||
|
- static char ttynm[32];
|
||||||
|
+ static char ttynm[UT_LINESIZE + 4];
|
||||||
|
static int init = 0;
|
||||||
|
|
||||||
|
if (!init) {
|
||||||
|
@@ -79,9 +79,13 @@ static void getuidtty(char **userp, char
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((tty = ttyname(0)) != NULL) {
|
||||||
|
- if (strncmp(tty, "/dev/", 5) == 0)
|
||||||
|
- tty += 5;
|
||||||
|
- sprintf(ttynm, "(%.28s) ", tty);
|
||||||
|
+ if (strncmp(tty, _PATH_DEV, strlen(_PATH_DEV)) == 0) {
|
||||||
|
+ tty += strlen(_PATH_DEV);
|
||||||
|
+ if (tty[0] == '/')
|
||||||
|
+ tty ++;
|
||||||
|
+ }
|
||||||
|
+ snprintf(ttynm, sizeof(ttynm), "(%.*s) ",
|
||||||
|
+ UT_LINESIZE, tty);
|
||||||
|
} else
|
||||||
|
ttynm[0] = 0;
|
||||||
|
init++;
|
||||||
|
@@ -129,7 +133,7 @@ void wall(char *text, int fromshutdown,
|
||||||
|
struct sigaction sa;
|
||||||
|
struct utmp *utmp;
|
||||||
|
time_t t;
|
||||||
|
- char term[UT_LINESIZE+6];
|
||||||
|
+ char term[UT_LINESIZE + strlen(_PATH_DEV) + 1];
|
||||||
|
char line[81];
|
||||||
|
char *date, *p;
|
||||||
|
char *user, *tty;
|
||||||
|
@@ -178,11 +182,11 @@ void wall(char *text, int fromshutdown,
|
||||||
|
while ((utmp = getutent()) != NULL) {
|
||||||
|
if(utmp->ut_type != USER_PROCESS ||
|
||||||
|
utmp->ut_user[0] == 0) continue;
|
||||||
|
- if (strncmp(utmp->ut_line, "/dev/", 5) == 0) {
|
||||||
|
+ if (strncmp(utmp->ut_line, _PATH_DEV, strlen(_PATH_DEV)) == 0) {
|
||||||
|
term[0] = 0;
|
||||||
|
- strncat(term, utmp->ut_line, UT_LINESIZE);
|
||||||
|
+ strncat(term, utmp->ut_line, sizeof(term)-1);
|
||||||
|
} else
|
||||||
|
- snprintf(term, sizeof(term), "/dev/%.*s",
|
||||||
|
+ snprintf(term, sizeof(term), _PATH_DEV "%.*s",
|
||||||
|
UT_LINESIZE, utmp->ut_line);
|
||||||
|
if (strstr(term, "/../")) continue;
|
||||||
|
|
||||||
|
--- src/init.c
|
||||||
|
+++ src/init.c 2009-05-11 00:00:00.000000000 +0200
|
||||||
|
@@ -54,12 +54,12 @@
|
||||||
|
#include <sepol/sepol.h>
|
||||||
|
|
||||||
|
#ifdef __i386__
|
||||||
|
-# if (__GLIBC__ >= 2)
|
||||||
|
- /* GNU libc 2.x */
|
||||||
|
+# if defined (__GLIBC__)
|
||||||
|
# define STACK_DEBUG 1
|
||||||
|
# if (__GLIBC__ == 2 && __GLIBC_MINOR__ == 0)
|
||||||
|
- /* Only glibc 2.0 needs this */
|
||||||
|
# include <sigcontext.h>
|
||||||
|
+# elif ( __GLIBC__ > 2) && ((__GLIBC__ == 2) && (__GLIBC_MINOR__ >= 1))
|
||||||
|
+# include <bits/sigcontext.h>
|
||||||
|
# endif
|
||||||
|
# endif
|
||||||
|
#endif
|
||||||
|
@@ -70,6 +70,12 @@
|
||||||
|
#include "reboot.h"
|
||||||
|
#include "set.h"
|
||||||
|
|
||||||
|
+#ifdef __GNUC__
|
||||||
|
+ __attribute__ ((format (printf, 2, 3)))
|
||||||
|
+#endif
|
||||||
|
+static void initlog(int loglevel, char *fmt, ...);
|
||||||
|
+static void print(char *fmt);
|
||||||
|
+
|
||||||
|
#ifndef SIGPWR
|
||||||
|
# define SIGPWR SIGUSR2
|
||||||
|
#endif
|
||||||
|
@@ -84,11 +90,15 @@
|
||||||
|
/* Set a signal handler. */
|
||||||
|
#define SETSIG(sa, sig, fun, flags) \
|
||||||
|
do { \
|
||||||
|
+ memset(&sa, 0, sizeof(sa)); \
|
||||||
|
sa.sa_handler = fun; \
|
||||||
|
sa.sa_flags = flags; \
|
||||||
|
sigemptyset(&sa.sa_mask); \
|
||||||
|
sigaction(sig, &sa, NULL); \
|
||||||
|
} while(0)
|
||||||
|
+#ifndef mem_barrier
|
||||||
|
+# define mem_barrier() __asm__ __volatile__("": : :"memory")
|
||||||
|
+#endif
|
||||||
|
|
||||||
|
/* Version information */
|
||||||
|
char *Version = "@(#) init " VERSION " " DATE " miquels@cistron.nl";
|
||||||
|
@@ -212,6 +222,7 @@ char *extra_env[NR_EXTRA_ENV];
|
||||||
|
* This only works correctly because the linux select updates
|
||||||
|
* the elapsed time in the struct timeval passed to select!
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void do_sleep(int sec)
|
||||||
|
{
|
||||||
|
struct timeval tv;
|
||||||
|
@@ -220,13 +231,14 @@ void do_sleep(int sec)
|
||||||
|
tv.tv_usec = 0;
|
||||||
|
|
||||||
|
while(select(0, NULL, NULL, NULL, &tv) < 0 && errno == EINTR)
|
||||||
|
- ;
|
||||||
|
+ mem_barrier();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Non-failing allocation routines (init cannot fail).
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void *imalloc(size_t size)
|
||||||
|
{
|
||||||
|
void *m;
|
||||||
|
@@ -239,7 +251,7 @@ void *imalloc(size_t size)
|
||||||
|
return m;
|
||||||
|
}
|
||||||
|
|
||||||
|
-
|
||||||
|
+static
|
||||||
|
char *istrdup(char *s)
|
||||||
|
{
|
||||||
|
char *m;
|
||||||
|
@@ -256,6 +268,7 @@ char *istrdup(char *s)
|
||||||
|
* Send the state info of the previous running init to
|
||||||
|
* the new one, in a version-independant way.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void send_state(int fd)
|
||||||
|
{
|
||||||
|
FILE *fp;
|
||||||
|
@@ -320,7 +333,7 @@ static int get_void(FILE *f)
|
||||||
|
int c;
|
||||||
|
|
||||||
|
while ((c = getc(f)) != EOF && c != '\n')
|
||||||
|
- ;
|
||||||
|
+ mem_barrier();
|
||||||
|
|
||||||
|
return (c != EOF);
|
||||||
|
}
|
||||||
|
@@ -337,7 +350,7 @@ static int get_cmd(FILE *f)
|
||||||
|
return C_EOF;
|
||||||
|
|
||||||
|
for(i = 0; cmds[i].cmd && strcmp(cmds[i].name, cmd) != 0; i++)
|
||||||
|
- ;
|
||||||
|
+ mem_barrier();
|
||||||
|
return cmds[i].cmd;
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -448,6 +461,7 @@ static CHILD *get_record(FILE *f)
|
||||||
|
* Read the complete state info from the state pipe.
|
||||||
|
* Returns 0 on success
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int receive_state(int fd)
|
||||||
|
{
|
||||||
|
FILE *f;
|
||||||
|
@@ -461,7 +475,7 @@ int receive_state(int fd)
|
||||||
|
get_string(old_version, sizeof(old_version), f);
|
||||||
|
oops_error = 0;
|
||||||
|
for (pp = &family; (*pp = get_record(f)) != NULL; pp = &((*pp)->next))
|
||||||
|
- ;
|
||||||
|
+ mem_barrier();
|
||||||
|
fclose(f);
|
||||||
|
return oops_error;
|
||||||
|
}
|
||||||
|
@@ -495,6 +509,7 @@ static int setproctitle(char *fmt, ...)
|
||||||
|
/*
|
||||||
|
* Set console_dev to a working console.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void console_init(void)
|
||||||
|
{
|
||||||
|
int fd;
|
||||||
|
@@ -534,6 +549,7 @@ void console_init(void)
|
||||||
|
/*
|
||||||
|
* Open the console with retries.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int console_open(int mode)
|
||||||
|
{
|
||||||
|
int f, fd = -1;
|
||||||
|
@@ -563,6 +579,7 @@ int console_open(int mode)
|
||||||
|
/*
|
||||||
|
* We got a signal (HUP PWR WINCH ALRM INT)
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void signal_handler(int sig)
|
||||||
|
{
|
||||||
|
ADDSET(got_signals, sig);
|
||||||
|
@@ -571,6 +588,7 @@ void signal_handler(int sig)
|
||||||
|
/*
|
||||||
|
* SIGCHLD: one of our children has died.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void chld_handler()
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -610,7 +628,8 @@ void chld_handler()
|
||||||
|
*
|
||||||
|
* The SIGCONT handler
|
||||||
|
*/
|
||||||
|
-void cont_handler()
|
||||||
|
+static
|
||||||
|
+void cont_handler(int sig)
|
||||||
|
{
|
||||||
|
got_cont = 1;
|
||||||
|
}
|
||||||
|
@@ -618,6 +637,7 @@ void cont_handler()
|
||||||
|
/*
|
||||||
|
* Fork and dump core in /.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void coredump(void)
|
||||||
|
{
|
||||||
|
static int dumped = 0;
|
||||||
|
@@ -651,6 +671,7 @@ void coredump(void)
|
||||||
|
* If we have the info, print where it occured.
|
||||||
|
* Then sleep 30 seconds and try to continue.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
#if defined(STACK_DEBUG) && defined(__linux__)
|
||||||
|
void segv_handler(int sig, struct sigcontext ctx)
|
||||||
|
{
|
||||||
|
@@ -667,7 +688,7 @@ void segv_handler(int sig, struct sigcon
|
||||||
|
errno = saved_errno;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
-void segv_handler()
|
||||||
|
+void segv_handler(int sig)
|
||||||
|
{
|
||||||
|
int saved_errno = errno;
|
||||||
|
|
||||||
|
@@ -682,7 +703,8 @@ void segv_handler()
|
||||||
|
/*
|
||||||
|
* The SIGSTOP & SIGTSTP handler
|
||||||
|
*/
|
||||||
|
-void stop_handler()
|
||||||
|
+static
|
||||||
|
+void stop_handler(int sig)
|
||||||
|
{
|
||||||
|
int saved_errno = errno;
|
||||||
|
|
||||||
|
@@ -695,6 +717,7 @@ void stop_handler()
|
||||||
|
/*
|
||||||
|
* Set terminal settings to reasonable defaults
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void console_stty(void)
|
||||||
|
{
|
||||||
|
struct termios tty;
|
||||||
|
@@ -710,16 +733,23 @@ void console_stty(void)
|
||||||
|
tty.c_cflag &= CBAUD|CBAUDEX|CSIZE|CSTOPB|PARENB|PARODD;
|
||||||
|
tty.c_cflag |= HUPCL|CLOCAL|CREAD;
|
||||||
|
|
||||||
|
- tty.c_cc[VINTR] = 3; /* ctrl('c') */
|
||||||
|
- tty.c_cc[VQUIT] = 28; /* ctrl('\\') */
|
||||||
|
- tty.c_cc[VERASE] = 127;
|
||||||
|
- tty.c_cc[VKILL] = 24; /* ctrl('x') */
|
||||||
|
- tty.c_cc[VEOF] = 4; /* ctrl('d') */
|
||||||
|
- tty.c_cc[VTIME] = 0;
|
||||||
|
- tty.c_cc[VMIN] = 1;
|
||||||
|
- tty.c_cc[VSTART] = 17; /* ctrl('q') */
|
||||||
|
- tty.c_cc[VSTOP] = 19; /* ctrl('s') */
|
||||||
|
- tty.c_cc[VSUSP] = 26; /* ctrl('z') */
|
||||||
|
+ tty.c_cc[VTIME] = 0;
|
||||||
|
+ tty.c_cc[VMIN] = 1;
|
||||||
|
+ tty.c_cc[VINTR] = CINTR;
|
||||||
|
+ tty.c_cc[VQUIT] = CQUIT;
|
||||||
|
+ tty.c_cc[VERASE] = CERASE; /* ASCII DEL (0177) */
|
||||||
|
+ tty.c_cc[VKILL] = CKILL;
|
||||||
|
+ tty.c_cc[VEOF] = CEOF;
|
||||||
|
+ tty.c_cc[VSWTC] = _POSIX_VDISABLE;
|
||||||
|
+ tty.c_cc[VSTART] = CSTART;
|
||||||
|
+ tty.c_cc[VSTOP] = CSTOP;
|
||||||
|
+ tty.c_cc[VSUSP] = CSUSP;
|
||||||
|
+ tty.c_cc[VEOL] = _POSIX_VDISABLE;
|
||||||
|
+ tty.c_cc[VREPRINT] = CREPRINT;
|
||||||
|
+ tty.c_cc[VDISCARD] = CDISCARD;
|
||||||
|
+ tty.c_cc[VWERASE] = CWERASE;
|
||||||
|
+ tty.c_cc[VLNEXT] = CLNEXT;
|
||||||
|
+ tty.c_cc[VEOL2] = _POSIX_VDISABLE;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Set pre and post processing
|
||||||
|
@@ -729,6 +759,14 @@ void console_stty(void)
|
||||||
|
tty.c_lflag = ISIG|ICANON|ECHO|ECHOCTL|ECHOPRT|ECHOKE;
|
||||||
|
|
||||||
|
/*
|
||||||
|
+ * Setting for SuSE: No flow control (-ixon), ignore break (ignbrk),
|
||||||
|
+ * and make nl/cr more usable (sane).
|
||||||
|
+ */
|
||||||
|
+ tty.c_iflag |= IGNBRK;
|
||||||
|
+ tty.c_iflag &= ~(BRKINT|INLCR|IGNCR|IXON);
|
||||||
|
+ tty.c_oflag &= ~(OCRNL|ONLRET);
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
* Now set the terminal line.
|
||||||
|
* We don't care about non-transmitted output data
|
||||||
|
* and non-read input data.
|
||||||
|
@@ -741,6 +779,7 @@ void console_stty(void)
|
||||||
|
/*
|
||||||
|
* Print to the system console
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void print(char *s)
|
||||||
|
{
|
||||||
|
int fd;
|
||||||
|
@@ -757,6 +796,7 @@ void print(char *s)
|
||||||
|
#ifdef __GNUC__
|
||||||
|
__attribute__ ((format (printf, 2, 3)))
|
||||||
|
#endif
|
||||||
|
+static
|
||||||
|
void initlog(int loglevel, char *s, ...)
|
||||||
|
{
|
||||||
|
va_list va_alist;
|
||||||
|
@@ -799,6 +839,7 @@ char **init_buildenv(int child)
|
||||||
|
char i_lvl[] = "RUNLEVEL=x";
|
||||||
|
char i_prev[] = "PREVLEVEL=x";
|
||||||
|
char i_cons[32];
|
||||||
|
+ char i_shell[] = "SHELL=" SHELL;
|
||||||
|
char **e;
|
||||||
|
int n, i;
|
||||||
|
|
||||||
|
@@ -818,6 +859,7 @@ char **init_buildenv(int child)
|
||||||
|
snprintf(i_cons, sizeof(i_cons), "CONSOLE=%s", console_dev);
|
||||||
|
i_lvl[9] = thislevel;
|
||||||
|
i_prev[10] = prevlevel;
|
||||||
|
+ e[n++] = istrdup(i_shell);
|
||||||
|
e[n++] = istrdup(i_lvl);
|
||||||
|
e[n++] = istrdup(i_prev);
|
||||||
|
e[n++] = istrdup(i_cons);
|
||||||
|
@@ -846,6 +888,7 @@ void init_freeenv(char **e)
|
||||||
|
* This function is too long and indents too deep.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int spawn(CHILD *ch, int *res)
|
||||||
|
{
|
||||||
|
char *args[16]; /* Argv array */
|
||||||
|
@@ -988,7 +1031,7 @@ int spawn(CHILD *ch, int *res)
|
||||||
|
}
|
||||||
|
SETSIG(sa, SIGCHLD, SIG_DFL, SA_RESTART);
|
||||||
|
if ((pid = fork()) < 0) {
|
||||||
|
- initlog(L_VB, "cannot fork");
|
||||||
|
+ initlog(L_VB, "cannot fork: %s", strerror(errno));
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
if (pid > 0) {
|
||||||
|
@@ -1017,7 +1060,7 @@ int spawn(CHILD *ch, int *res)
|
||||||
|
* this with a temporary process.
|
||||||
|
*/
|
||||||
|
if ((pid = fork()) < 0) {
|
||||||
|
- initlog(L_VB, "cannot fork");
|
||||||
|
+ initlog(L_VB, "cannot fork: %s", strerror(errno));
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
if (pid == 0) {
|
||||||
|
@@ -1083,6 +1126,7 @@ int spawn(CHILD *ch, int *res)
|
||||||
|
/*
|
||||||
|
* Start a child running!
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void startup(CHILD *ch)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
@@ -1125,6 +1169,7 @@ void startup(CHILD *ch)
|
||||||
|
/*
|
||||||
|
* Read the inittab file.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void read_inittab(void)
|
||||||
|
{
|
||||||
|
FILE *fp; /* The INITTAB file */
|
||||||
|
@@ -1182,7 +1227,7 @@ void read_inittab(void)
|
||||||
|
* Skip comments and empty lines
|
||||||
|
*/
|
||||||
|
for(p = buf; *p == ' ' || *p == '\t'; p++)
|
||||||
|
- ;
|
||||||
|
+ mem_barrier();
|
||||||
|
if (*p == '#' || *p == '\n') continue;
|
||||||
|
|
||||||
|
/*
|
||||||
|
@@ -1505,6 +1550,7 @@ void read_inittab(void)
|
||||||
|
* The entries that do not belong here at all are removed
|
||||||
|
* from the list.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void start_if_needed(void)
|
||||||
|
{
|
||||||
|
CHILD *ch; /* Pointer to child */
|
||||||
|
@@ -1550,6 +1596,7 @@ void start_if_needed(void)
|
||||||
|
/*
|
||||||
|
* Ask the user on the console for a runlevel
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int ask_runlevel(void)
|
||||||
|
{
|
||||||
|
const char prompt[] = "\nEnter runlevel: ";
|
||||||
|
@@ -1578,6 +1625,7 @@ int ask_runlevel(void)
|
||||||
|
* Search the INITTAB file for the 'initdefault' field, with the default
|
||||||
|
* runlevel. If this fails, ask the user to supply a runlevel.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int get_init_default(void)
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -1626,6 +1674,7 @@ int get_init_default(void)
|
||||||
|
* the "old" INITLVL and arg == 0, try to read the new
|
||||||
|
* runlevel from that file first.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int read_level(int arg)
|
||||||
|
{
|
||||||
|
CHILD *ch; /* Walk through list */
|
||||||
|
@@ -1694,7 +1743,16 @@ int read_level(int arg)
|
||||||
|
initlog(L_VB, "Switching to runlevel: %c", foo);
|
||||||
|
}
|
||||||
|
|
||||||
|
- if (foo == 'Q') return runlevel;
|
||||||
|
+ if (foo == 'Q') {
|
||||||
|
+ struct sigaction sa;
|
||||||
|
+
|
||||||
|
+ /*
|
||||||
|
+ * Re-enable SIGINT's, which may disabled by
|
||||||
|
+ * an former Ctrl-Alt-Del action in process_signals().
|
||||||
|
+ */
|
||||||
|
+ SETSIG(sa, SIGINT, signal_handler, 0);
|
||||||
|
+ return(runlevel);
|
||||||
|
+ }
|
||||||
|
|
||||||
|
/* Check if this is a runlevel a, b or c */
|
||||||
|
if (strchr("ABC", foo)) {
|
||||||
|
@@ -1733,6 +1791,7 @@ int read_level(int arg)
|
||||||
|
* longer than 5 minutes, or inittab was read again due
|
||||||
|
* to user interaction.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void fail_check(void)
|
||||||
|
{
|
||||||
|
CHILD *ch; /* Pointer to child structure */
|
||||||
|
@@ -1765,6 +1824,7 @@ void fail_check(void)
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Set all 'Fail' timers to 0 */
|
||||||
|
+static
|
||||||
|
void fail_cancel(void)
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -1779,6 +1839,7 @@ void fail_cancel(void)
|
||||||
|
/*
|
||||||
|
* Start up powerfail entries.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void do_power_fail(int pwrstat)
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -1812,6 +1873,7 @@ void do_power_fail(int pwrstat)
|
||||||
|
/*
|
||||||
|
* Check for state-pipe presence
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int check_pipe(int fd)
|
||||||
|
{
|
||||||
|
struct timeval t;
|
||||||
|
@@ -1832,6 +1894,7 @@ int check_pipe(int fd)
|
||||||
|
/*
|
||||||
|
* Make a state-pipe.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
int make_pipe(int fd)
|
||||||
|
{
|
||||||
|
int fds[2];
|
||||||
|
@@ -1849,6 +1912,7 @@ int make_pipe(int fd)
|
||||||
|
/*
|
||||||
|
* Attempt to re-exec.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void re_exec(void)
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -1906,7 +1970,7 @@ void re_exec(void)
|
||||||
|
* The existing init process execs a new init binary.
|
||||||
|
*/
|
||||||
|
env = init_buildenv(0);
|
||||||
|
- execl(myname, myname, "--init", NULL, env);
|
||||||
|
+ execle(myname, myname, "--init", NULL, env);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* We shouldn't be here, something failed.
|
||||||
|
@@ -1943,6 +2007,7 @@ void redo_utmp_wtmp(void)
|
||||||
|
* We got a change runlevel request through the
|
||||||
|
* init.fifo. Process it.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void fifo_new_level(int level)
|
||||||
|
{
|
||||||
|
#if CHANGE_WAIT
|
||||||
|
@@ -1972,7 +2037,7 @@ void fifo_new_level(int level)
|
||||||
|
if (runlevel > '1' && runlevel < '6') redo_utmp_wtmp();
|
||||||
|
read_inittab();
|
||||||
|
fail_cancel();
|
||||||
|
- setproctitle("init [%c]", runlevel);
|
||||||
|
+ setproctitle("init [%c]", (int)runlevel);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@@ -2040,6 +2105,7 @@ void initcmd_setenv(char *data, int size
|
||||||
|
* the 2.2 kernel credential stuff to see who we're talking to.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void check_init_fifo(void)
|
||||||
|
{
|
||||||
|
struct init_request request;
|
||||||
|
@@ -2105,7 +2171,7 @@ void check_init_fifo(void)
|
||||||
|
tv.tv_usec = 0;
|
||||||
|
n = select(pipe_fd + 1, &fds, NULL, NULL, &tv);
|
||||||
|
if (n <= 0) {
|
||||||
|
- if (n == 0 || errno == EINTR) return;
|
||||||
|
+ if (n == 0 || errno == EINTR || errno == EAGAIN) return;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -2122,7 +2188,7 @@ void check_init_fifo(void)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (n <= 0) {
|
||||||
|
- if (errno == EINTR) return;
|
||||||
|
+ if (errno == EINTR || errno == EAGAIN) return;
|
||||||
|
initlog(L_VB, "error reading initrequest");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
@@ -2194,6 +2260,7 @@ void check_init_fifo(void)
|
||||||
|
* This function is used in the transition
|
||||||
|
* sysinit (-> single user) boot -> multi-user.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void boot_transitions()
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -2270,7 +2337,7 @@ void boot_transitions()
|
||||||
|
write_utmp_wtmp("runlevel", "~~", runlevel + 256 * oldlevel, RUN_LVL, "~");
|
||||||
|
thislevel = runlevel;
|
||||||
|
prevlevel = oldlevel;
|
||||||
|
- setproctitle("init [%c]", runlevel);
|
||||||
|
+ setproctitle("init [%c]", (int)runlevel);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@@ -2279,6 +2346,7 @@ void boot_transitions()
|
||||||
|
* Init got hit by a signal. See which signal it is,
|
||||||
|
* and act accordingly.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void process_signals()
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
@@ -2303,7 +2371,12 @@ void process_signals()
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ISMEMBER(got_signals, SIGINT)) {
|
||||||
|
+ struct sigaction sa;
|
||||||
|
INITDBG(L_VB, "got SIGINT");
|
||||||
|
+
|
||||||
|
+ /* we don't want any more SIGINT's */
|
||||||
|
+ SETSIG(sa, SIGINT, SIG_IGN, SA_RESTART);
|
||||||
|
+
|
||||||
|
/* Tell ctrlaltdel entry to start up */
|
||||||
|
for(ch = family; ch; ch = ch->next)
|
||||||
|
if (ch->action == CTRLALTDEL)
|
||||||
|
@@ -2365,7 +2438,7 @@ void process_signals()
|
||||||
|
runlevel == '1') console_stty();
|
||||||
|
read_inittab();
|
||||||
|
fail_cancel();
|
||||||
|
- setproctitle("init [%c]", runlevel);
|
||||||
|
+ setproctitle("init [%c]", (int)runlevel);
|
||||||
|
DELSET(got_signals, SIGHUP);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@@ -2384,7 +2457,8 @@ void process_signals()
|
||||||
|
/*
|
||||||
|
* The main loop
|
||||||
|
*/
|
||||||
|
-int init_main()
|
||||||
|
+static
|
||||||
|
+void init_main(void)
|
||||||
|
{
|
||||||
|
CHILD *ch;
|
||||||
|
struct sigaction sa;
|
||||||
|
@@ -2539,6 +2613,7 @@ int init_main()
|
||||||
|
/*
|
||||||
|
* Tell the user about the syntax we expect.
|
||||||
|
*/
|
||||||
|
+static
|
||||||
|
void usage(char *s)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "Usage: %s 0123456SsQqAaBbCcUu\n", s);
|
||||||
|
@@ -2596,12 +2671,38 @@ int telinit(char *progname, int argc, ch
|
||||||
|
request.sleeptime = sltime;
|
||||||
|
}
|
||||||
|
|
||||||
|
+ /* Catch some common signals. */
|
||||||
|
+ signal(SIGQUIT, SIG_IGN);
|
||||||
|
+ signal(SIGCHLD, SIG_IGN);
|
||||||
|
+ signal(SIGHUP, SIG_IGN);
|
||||||
|
+ signal(SIGTSTP, SIG_IGN);
|
||||||
|
+ signal(SIGTTIN, SIG_IGN);
|
||||||
|
+ signal(SIGTTOU, SIG_IGN);
|
||||||
|
+ signal(SIGINT, SIG_IGN);
|
||||||
|
+
|
||||||
|
+ /* Go to the root directory. */
|
||||||
|
+ chdir("/");
|
||||||
|
+
|
||||||
|
/* Open the fifo and write a command. */
|
||||||
|
+
|
||||||
|
/* Make sure we don't hang on opening /dev/initctl */
|
||||||
|
SETSIG(sa, SIGALRM, signal_handler, 0);
|
||||||
|
alarm(3);
|
||||||
|
- if ((fd = open(INIT_FIFO, O_WRONLY)) >= 0 &&
|
||||||
|
- write(fd, &request, sizeof(request)) == sizeof(request)) {
|
||||||
|
+ if ((fd = open(INIT_FIFO, O_WRONLY)) >= 0) {
|
||||||
|
+ ssize_t p = 0;
|
||||||
|
+ size_t s = sizeof(request);
|
||||||
|
+ void *ptr = &request;
|
||||||
|
+
|
||||||
|
+ while (s > 0) {
|
||||||
|
+ p = write(fd, ptr, s);
|
||||||
|
+ if (p < 0) {
|
||||||
|
+ if (errno == EINTR || errno == EAGAIN)
|
||||||
|
+ continue;
|
||||||
|
+ break;
|
||||||
|
+ }
|
||||||
|
+ ptr += p;
|
||||||
|
+ s -= p;
|
||||||
|
+ }
|
||||||
|
close(fd);
|
||||||
|
alarm(0);
|
||||||
|
return 0;
|
||||||
|
@@ -2652,6 +2753,8 @@ int main(int argc, char **argv)
|
||||||
|
p++;
|
||||||
|
else
|
||||||
|
p = argv[0];
|
||||||
|
+
|
||||||
|
+ /* Common umask */
|
||||||
|
umask(022);
|
||||||
|
|
||||||
|
/* Quick check */
|
||||||
|
@@ -2684,7 +2787,7 @@ int main(int argc, char **argv)
|
||||||
|
for (f = 0; f < argc; f++)
|
||||||
|
maxproclen += strlen(argv[f]) + 1;
|
||||||
|
reload = 1;
|
||||||
|
- setproctitle("init [%c]",runlevel);
|
||||||
|
+ setproctitle("init [%c]", (int)runlevel);
|
||||||
|
|
||||||
|
init_main();
|
||||||
|
}
|
||||||
|
@@ -2727,7 +2830,7 @@ int main(int argc, char **argv)
|
||||||
|
argv0 = argv[0];
|
||||||
|
argv[1] = NULL;
|
||||||
|
setproctitle("init boot");
|
||||||
|
- init_main(dfl_level);
|
||||||
|
+ init_main();
|
||||||
|
|
||||||
|
/*NOTREACHED*/
|
||||||
|
return 0;
|
||||||
|
--- src/init.h
|
||||||
|
+++ src/init.h 2006-08-18 14:45:28.000000000 +0200
|
||||||
|
@@ -30,12 +30,6 @@
|
||||||
|
/* Prototypes. */
|
||||||
|
void write_utmp_wtmp(char *user, char *id, int pid, int type, char *line);
|
||||||
|
void write_wtmp(char *user, char *id, int pid, int type, char *line);
|
||||||
|
-#ifdef __GNUC__
|
||||||
|
-__attribute__ ((format (printf, 2, 3)))
|
||||||
|
-#endif
|
||||||
|
-void initlog(int loglevel, char *fmt, ...);
|
||||||
|
-void set_term(int how);
|
||||||
|
-void print(char *fmt);
|
||||||
|
|
||||||
|
#if DEBUG
|
||||||
|
# define INITDBG(level, fmt, args...) initlog(level, fmt, ##args)
|
||||||
|
--- src/shutdown.c
|
||||||
|
+++ src/shutdown.c 2006-08-18 14:45:28.000000000 +0200
|
||||||
|
@@ -60,6 +60,7 @@ char *clean_env[] = {
|
||||||
|
"HOME=/",
|
||||||
|
"PATH=/bin:/usr/bin:/sbin:/usr/sbin",
|
||||||
|
"TERM=dumb",
|
||||||
|
+ "SHELL=/bin/sh",
|
||||||
|
NULL,
|
||||||
|
};
|
||||||
|
|
||||||
|
@@ -159,11 +160,24 @@ int init_setenv(char *name, char *value)
|
||||||
|
sigaction(SIGALRM, &sa, NULL);
|
||||||
|
got_alrm = 0;
|
||||||
|
alarm(3);
|
||||||
|
- if ((fd = open(INIT_FIFO, O_WRONLY)) >= 0 &&
|
||||||
|
- write(fd, &request, sizeof(request)) == sizeof(request)) {
|
||||||
|
- close(fd);
|
||||||
|
- alarm(0);
|
||||||
|
- return 0;
|
||||||
|
+ if ((fd = open(INIT_FIFO, O_WRONLY)) >= 0) {
|
||||||
|
+ ssize_t p = 0;
|
||||||
|
+ size_t s = sizeof(request);
|
||||||
|
+ void *ptr = &request;
|
||||||
|
+
|
||||||
|
+ while (s > 0) {
|
||||||
|
+ p = write(fd, ptr, s);
|
||||||
|
+ if (p < 0) {
|
||||||
|
+ if (errno == EINTR || errno == EAGAIN)
|
||||||
|
+ continue;
|
||||||
|
+ break;
|
||||||
|
+ }
|
||||||
|
+ ptr += p;
|
||||||
|
+ s -= p;
|
||||||
|
+ }
|
||||||
|
+ close(fd);
|
||||||
|
+ alarm(0);
|
||||||
|
+ return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
fprintf(stderr, "shutdown: ");
|
||||||
|
--- src/utmp.c
|
||||||
|
+++ src/utmp.c 2006-08-18 14:45:28.000000000 +0200
|
||||||
|
@@ -47,6 +47,9 @@ char *line) /* Which line is this */
|
||||||
|
int fd;
|
||||||
|
struct utmp utmp;
|
||||||
|
struct utsname uname_buf;
|
||||||
|
+#if __WORDSIZE == 64 && defined __WORDSIZE_COMPAT32
|
||||||
|
+ struct timeval tv;
|
||||||
|
+#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Can't do much if WTMP_FILE is not present or not writable.
|
||||||
|
@@ -99,7 +102,13 @@ char *line) /* Which line is this */
|
||||||
|
*/
|
||||||
|
memset(&utmp, 0, sizeof(utmp));
|
||||||
|
#if defined(__GLIBC__)
|
||||||
|
+# if __WORDSIZE == 64 && defined __WORDSIZE_COMPAT32
|
||||||
|
+ gettimeofday(&tv, NULL);
|
||||||
|
+ utmp.ut_tv.tv_sec = (int32_t)tv.tv_sec;
|
||||||
|
+ utmp.ut_tv.tv_usec = (int32_t)tv.tv_usec;
|
||||||
|
+# else
|
||||||
|
gettimeofday(&utmp.ut_tv, NULL);
|
||||||
|
+# endif
|
||||||
|
#else
|
||||||
|
time(&utmp.ut_time);
|
||||||
|
#endif
|
||||||
|
@@ -136,6 +145,9 @@ char *oldline) /* Line of old utmp ent
|
||||||
|
struct utmp utmp;
|
||||||
|
struct utmp tmp;
|
||||||
|
struct utmp *utmptr;
|
||||||
|
+#if __WORDSIZE == 64 && defined __WORDSIZE_COMPAT32
|
||||||
|
+ struct timeval tv;
|
||||||
|
+#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Can't do much if UTMP_FILE is not present or not writable.
|
||||||
|
@@ -184,7 +196,13 @@ char *oldline) /* Line of old utmp ent
|
||||||
|
utmp.ut_pid = pid;
|
||||||
|
strncpy(utmp.ut_id, id, sizeof(utmp.ut_id));
|
||||||
|
#if defined(__GLIBC__)
|
||||||
|
+# if __WORDSIZE == 64 && defined __WORDSIZE_COMPAT32
|
||||||
|
+ gettimeofday(&tv, NULL);
|
||||||
|
+ utmp.ut_tv.tv_sec = (int32_t)tv.tv_sec;
|
||||||
|
+ utmp.ut_tv.tv_usec = (int32_t)tv.tv_usec;
|
||||||
|
+# else
|
||||||
|
gettimeofday(&utmp.ut_tv, NULL);
|
||||||
|
+# endif
|
||||||
|
#else
|
||||||
|
time(&utmp.ut_time);
|
||||||
|
#endif
|
||||||
|
--- doc/utmpdump.1
|
||||||
|
+++ doc/utmpdump.1 2010-02-08 13:41:51.154825000 +0000
|
||||||
|
@@ -0,0 +1,47 @@
|
||||||
|
+.TH UTMPDUMP 1 "Februar 8, 2010" "" "Linux System Administrator's Manual"
|
||||||
|
+.SH NAME
|
||||||
|
+utmpdump \- dump UTMP and WTMP files in raw format
|
||||||
|
+.SH SYNOPSIS
|
||||||
|
+.B utmpdump
|
||||||
|
+.RB [ \-froh ]
|
||||||
|
+.I filename
|
||||||
|
+.SH DESCRIPTION
|
||||||
|
+\fButmpdump\fP is a simple program to dump UTMP and WTMP files
|
||||||
|
+in raw format, so they can be examined.
|
||||||
|
+.SH OPTIONS
|
||||||
|
+.IP \fB\-f\fP
|
||||||
|
+output appended data as the file grows.
|
||||||
|
+.IP "\fB\-r\fP"
|
||||||
|
+reverse. Write back edited login information into utmp or wtmp files.
|
||||||
|
+.IP \fB\-o\fP
|
||||||
|
+use old libc5 format.
|
||||||
|
+.IP \fB\-h\fP
|
||||||
|
+usage information.
|
||||||
|
+.PP
|
||||||
|
+utmpdump can be useful in cases of corrupted utmp or wtmp entries.
|
||||||
|
+It can dump out utmp/wtmp to an ASCII file, then that file can
|
||||||
|
+be edited to remove bogus entries and reintegrated, using
|
||||||
|
+.PP
|
||||||
|
+.sp 1
|
||||||
|
+.in +1c
|
||||||
|
+.nf
|
||||||
|
+\fButmpdump -r < ascii file > wtmp\fP
|
||||||
|
+.fi
|
||||||
|
+.in -1c
|
||||||
|
+.sp 1
|
||||||
|
+but be warned as
|
||||||
|
+.B utmpdump
|
||||||
|
+was written for debugging purpose only.
|
||||||
|
+.SH BUGS
|
||||||
|
+You may
|
||||||
|
+.B not
|
||||||
|
+use the option \fB\-r\fP as the format for the
|
||||||
|
+utmp/wtmp files strongly depends on the
|
||||||
|
+input format. This tool is
|
||||||
|
+.B not
|
||||||
|
+supported, use it at your own risk only.
|
||||||
|
+.SH "SEE ALSO"
|
||||||
|
+.BR last (1),
|
||||||
|
+.BR w (1),
|
||||||
|
+.BR who (1),
|
||||||
|
+.BR utmp (5),
|
3
sysvinit-2.86.tar.bz2
Normal file
3
sysvinit-2.86.tar.bz2
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
version https://git-lfs.github.com/spec/v1
|
||||||
|
oid sha256:2e2357e6449737b0ca2fe2d727b709e722dda8d64428e1266ad7da28d25ddc2b
|
||||||
|
size 84163
|
@ -1,76 +0,0 @@
|
|||||||
--- src/killall5.c
|
|
||||||
+++ src/killall5.c 2010-03-19 14:29:44.000000000 +0000
|
|
||||||
@@ -444,6 +444,38 @@ int readarg(FILE *fp, char *buf, int sz)
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
+ * Scan the filedescriptors of pid for /dev/fuse
|
|
||||||
+ */
|
|
||||||
+int is_fuse(const char *pid) {
|
|
||||||
+ DIR *dir;
|
|
||||||
+ char path[256];
|
|
||||||
+ char buf[256];
|
|
||||||
+ struct dirent *d;
|
|
||||||
+ ssize_t len;
|
|
||||||
+
|
|
||||||
+ /* Open /proc/pid/fd/ */
|
|
||||||
+ snprintf(path, sizeof(path), "/proc/%s/fd", pid);
|
|
||||||
+ if ((dir = opendir(path)) != NULL) {
|
|
||||||
+ int dfd = dirfd(dir);
|
|
||||||
+ /* Walk through the directory. */
|
|
||||||
+ while ((d = readdir(dir)) != NULL) {
|
|
||||||
+ if (*d->d_name == '.')
|
|
||||||
+ continue;
|
|
||||||
+ /* check for /dev/fuse */
|
|
||||||
+ if ((len = readlinkat(dfd, d->d_name, buf, sizeof(buf))) > 0) {
|
|
||||||
+ buf[len] = '\0';
|
|
||||||
+ if (strcmp("/dev/fuse", buf) == 0)
|
|
||||||
+ return 1; /* Fuse filesystem */
|
|
||||||
+ }
|
|
||||||
+ }
|
|
||||||
+ closedir(dir);
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ /* Not a fuse filesystem */
|
|
||||||
+ return 0;
|
|
||||||
+}
|
|
||||||
+
|
|
||||||
+/*
|
|
||||||
* Read the proc filesystem.
|
|
||||||
* CWD must be /proc to avoid problems if / is affected by the killing (ie depend on fuse).
|
|
||||||
*/
|
|
||||||
@@ -458,6 +490,7 @@ int readproc(int do_stat)
|
|
||||||
char buf[PATH_MAX+1];
|
|
||||||
char *s, *q;
|
|
||||||
unsigned long startcode, endcode;
|
|
||||||
+ ssize_t len;
|
|
||||||
int pid, f;
|
|
||||||
|
|
||||||
/* Open the /proc directory. */
|
|
||||||
@@ -608,6 +641,26 @@ int readproc(int do_stat)
|
|
||||||
p->nfs = 0;
|
|
||||||
|
|
||||||
switch (do_stat) {
|
|
||||||
+ case NO_STAT:
|
|
||||||
+ if ((len = readlink(path, buf, PATH_MAX)) < 0)
|
|
||||||
+ break;
|
|
||||||
+ buf[len] = '\0';
|
|
||||||
+
|
|
||||||
+ /* Check for uevent handler, mdmon, and for providers
|
|
||||||
+ of FUSE filesystems */
|
|
||||||
+ if ((strncmp(buf, "/sbin/udevd", 11) == 0) ||
|
|
||||||
+ (strncmp(buf, "/sbin/mdmon", 11) == 0) ||
|
|
||||||
+ (is_fuse(d->d_name))) {
|
|
||||||
+ OMIT *restrict optr;
|
|
||||||
+
|
|
||||||
+ xmemalign((void*)&optr, sizeof(void*), alignof(OMIT));
|
|
||||||
+ optr->next = omit;
|
|
||||||
+ optr->prev = (OMIT*)0;
|
|
||||||
+ optr->pid = pid;
|
|
||||||
+ omit = optr;
|
|
||||||
+ }
|
|
||||||
+
|
|
||||||
+ break;
|
|
||||||
case DO_NETFS:
|
|
||||||
if ((p->nfs = check4nfs(path, buf)))
|
|
||||||
break;
|
|
@ -1,52 +0,0 @@
|
|||||||
--- src/Makefile
|
|
||||||
+++ src/Makefile 2010-03-23 15:11:12.000000000 +0000
|
|
||||||
@@ -9,16 +9,16 @@
|
|
||||||
#
|
|
||||||
|
|
||||||
CPPFLAGS = -DUSE_PAM
|
|
||||||
-CFLAGS ?= -ansi -O2 -fomit-frame-pointer
|
|
||||||
+CFLAGS ?= $(RPM_OPT_FLAGS)
|
|
||||||
override CFLAGS += -W -Wall -D_GNU_SOURCE
|
|
||||||
STATIC =
|
|
||||||
|
|
||||||
# For some known distributions we do not build all programs, otherwise we do.
|
|
||||||
BIN =
|
|
||||||
SBIN = init halt shutdown runlevel killall5 fstab-decode
|
|
||||||
-USRBIN = last mesg
|
|
||||||
+USRBIN = last
|
|
||||||
|
|
||||||
-MAN1 = last.1 lastb.1 mesg.1
|
|
||||||
+MAN1 = last.1 lastb.1
|
|
||||||
MAN5 = initscript.5 inittab.5
|
|
||||||
MAN8 = halt.8 init.8 killall5.8 pidof.8 poweroff.8 reboot.8 runlevel.8
|
|
||||||
MAN8 += shutdown.8 telinit.8 fstab-decode.8
|
|
||||||
@@ -170,7 +170,8 @@ endif
|
|
||||||
ln -sf halt $(ROOT)/sbin/reboot
|
|
||||||
ln -sf halt $(ROOT)/sbin/poweroff
|
|
||||||
ln -sf init $(ROOT)/sbin/telinit
|
|
||||||
- ln -sf /sbin/killall5 $(ROOT)/bin/pidof
|
|
||||||
+ ln -sf killall5 $(ROOT)/sbin/pidof
|
|
||||||
+ ln -sf ../sbin/killall5 $(ROOT)/bin/pidof
|
|
||||||
if [ ! -f $(ROOT)/usr/bin/lastb ]; then \
|
|
||||||
ln -sf last $(ROOT)/usr/bin/lastb; \
|
|
||||||
fi
|
|
||||||
--- src/bootlogd.c
|
|
||||||
+++ src/bootlogd.c 2006-08-18 12:45:28.000000000 +0000
|
|
||||||
@@ -241,7 +241,7 @@ int isconsole(char *s, char *res, int rl
|
|
||||||
int consolename(char *res, int rlen)
|
|
||||||
{
|
|
||||||
#ifdef TIOCGDEV
|
|
||||||
- unsigned int kdev;
|
|
||||||
+ kdev_t kdev;
|
|
||||||
#endif
|
|
||||||
struct stat st, st2;
|
|
||||||
char buf[256];
|
|
||||||
@@ -555,7 +555,7 @@ int main(int argc, char **argv)
|
|
||||||
}
|
|
||||||
|
|
||||||
(void)ioctl(0, TIOCCONS, NULL);
|
|
||||||
-#if 1
|
|
||||||
+#if 0
|
|
||||||
/* Work around bug in 2.1/2.2 kernels. Fixed in 2.2.13 and 2.3.18 */
|
|
||||||
if ((n = open("/dev/tty0", O_RDWR)) >= 0) {
|
|
||||||
(void)ioctl(n, TIOCCONS, NULL);
|
|
@ -1,3 +0,0 @@
|
|||||||
version https://git-lfs.github.com/spec/v1
|
|
||||||
oid sha256:60bbc8c1e1792056e23761d22960b30bb13eccc2cabff8c7310a01f4d5df1519
|
|
||||||
size 105551
|
|
@ -1,40 +0,0 @@
|
|||||||
diff --git a/trunk/src/last.c b/trunk/src/last.c
|
|
||||||
index 5003c7c..02103e0 100644
|
|
||||||
--- a/trunk/src/last.c
|
|
||||||
+++ b/trunk/src/last.c
|
|
||||||
@@ -318,30 +318,22 @@ int dns_lookup(char *result, int size, int useip, int32_t *a)
|
|
||||||
struct sockaddr_in6 sin6;
|
|
||||||
struct sockaddr *sa;
|
|
||||||
int salen, flags;
|
|
||||||
- unsigned int topnibble;
|
|
||||||
- unsigned int azero = 0, sitelocal = 0;
|
|
||||||
int mapped = 0;
|
|
||||||
|
|
||||||
flags = useip ? NI_NUMERICHOST : 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
- * IPv4 or IPv6 ? We use 2 heuristics:
|
|
||||||
- * 1. Current IPv6 range uses 2000-3fff or fec0-feff.
|
|
||||||
- * Outside of that is illegal and must be IPv4.
|
|
||||||
- * 2. If last 3 bytes are 0, must be IPv4
|
|
||||||
- * 3. If IPv6 in IPv4, handle as IPv4
|
|
||||||
+ * IPv4 or IPv6 ?
|
|
||||||
+ * 1. If last 3 4bytes are 0, must be IPv4
|
|
||||||
+ * 2. If IPv6 in IPv4, handle as IPv4
|
|
||||||
+ * 3. Anything else is IPv6
|
|
||||||
*
|
|
||||||
* Ugly.
|
|
||||||
*/
|
|
||||||
if (a[0] == 0 && a[1] == 0 && a[2] == (int32_t)htonl (0xffff))
|
|
||||||
mapped = 1;
|
|
||||||
- topnibble = ntohl((unsigned int)a[0]) >> 28;
|
|
||||||
|
|
||||||
- azero = ntohl((unsigned int)a[0]) >> 16;
|
|
||||||
- sitelocal = (azero >= 0xfec0 && azero <= 0xfeff) ? 1 : 0;
|
|
||||||
-
|
|
||||||
- if (((topnibble < 2 || topnibble > 3) && (!sitelocal)) || mapped ||
|
|
||||||
- (a[1] == 0 && a[2] == 0 && a[3] == 0)) {
|
|
||||||
+ if (mapped || (a[1] == 0 && a[2] == 0 && a[3] == 0)) {
|
|
||||||
/* IPv4 */
|
|
||||||
sin.sin_family = AF_INET;
|
|
||||||
sin.sin_port = 0;
|
|
160
sysvinit.changes
160
sysvinit.changes
@ -1,8 +1,3 @@
|
|||||||
-------------------------------------------------------------------
|
|
||||||
Tue Apr 13 18:27:02 CEST 2010 - werner@suse.de
|
|
||||||
|
|
||||||
- Add patch to make last(1) knowing latest IPv6 specs
|
|
||||||
|
|
||||||
-------------------------------------------------------------------
|
-------------------------------------------------------------------
|
||||||
Mon Apr 12 17:49:46 CEST 2010 - werner@suse.de
|
Mon Apr 12 17:49:46 CEST 2010 - werner@suse.de
|
||||||
|
|
||||||
@ -12,167 +7,12 @@ Mon Apr 12 17:49:46 CEST 2010 - werner@suse.de
|
|||||||
Fri Apr 9 15:45:51 CEST 2010 - werner@suse.de
|
Fri Apr 9 15:45:51 CEST 2010 - werner@suse.de
|
||||||
|
|
||||||
- Correct Pre-Requires to reflect package split
|
- Correct Pre-Requires to reflect package split
|
||||||
- Update to sysvinit (2.88dsf) world; urgency=low
|
|
||||||
|
|
||||||
* Mention new home on Savannah in README.
|
|
||||||
* Revert change from Fedora/RedHat where the now obsolete command
|
|
||||||
INIT_CMD_CHANGECONS was introduced. Based on feedback and patch
|
|
||||||
from Bill Nottingham.
|
|
||||||
* Adjust makefile to make sure the install directories are created
|
|
||||||
before files are copied into them.
|
|
||||||
* Simplify build rules, based on patch from Mike Frysinger and Gentoo.
|
|
||||||
* Fix minor bug in optimizing of argument parsing. Based on
|
|
||||||
report from jakemus on freshmeat.
|
|
||||||
* Add casts to get rid of compiler warning about signed/unsigned issues.
|
|
||||||
* Change tty handling in init to make sure the UTF-8 flag is not cleared
|
|
||||||
on boot. Patch from Samuel Thibault.
|
|
||||||
* Add Makefile in toplevel directory.
|
|
||||||
* Print usage information when shutdown is used by non-root user.
|
|
||||||
Patch from Mike Frysinger and Gentoo.
|
|
||||||
* Sync shutdown manual page and usage information. Patch from Mike
|
|
||||||
Frysinger and Gentoo.
|
|
||||||
* Fix race condition in utmp writing. Patch from Gil Kloepfer via
|
|
||||||
Mike Frysinger and Gentoo.
|
|
||||||
* Rewrite findtty() in bootlogd to recursively search /dev/ for the
|
|
||||||
correct device, to handle terminal devices for example in /dev/pty/.
|
|
||||||
Patch from Debian.
|
|
||||||
* Make sure bootlogd findpty() returns an error value when it fails to
|
|
||||||
find a usable pty. Patch from Rob Leslie via Debian.
|
|
||||||
* Make sure bootlogd fflush() every line, even if asked not to flush
|
|
||||||
to disk using fdatasync(). Patch from Scott Gifford via Debian.
|
|
||||||
* Add compatibility code to handle old path "/etc/powerstatus" for a
|
|
||||||
while.
|
|
||||||
* Incude definition for MNT_DETACH which is missing in older GNU libc
|
|
||||||
headers.
|
|
||||||
* Do not strip binaries before installing them, to make it easier to
|
|
||||||
get binaries with debug information installed.
|
|
||||||
* Add the comment from Andrea Arcangeli about the correct
|
|
||||||
place of setting the default childhandler within spawn().
|
|
||||||
* Make sure that newline is printed out for last(1) even
|
|
||||||
if an utmp record entry is truncated.
|
|
||||||
* Check if utmp not only exists but also is writable and delay
|
|
||||||
writing out of the utmp runlevel record if utmp is not writable.
|
|
||||||
* Be able to find libcrypt also on 64 bit based architectures.
|
|
||||||
* Add option -w to the last command to display the full user and
|
|
||||||
domain names in the output. Patch from Petr Lautrbach.
|
|
||||||
* Add a manual page for utmpdump as this tool is sometimes
|
|
||||||
very useful even if not intended for normal use.
|
|
||||||
* Use paths.h macros for wall
|
|
||||||
* Change path "/etc/powerstatus" to "/var/run/powerstatus"
|
|
||||||
* Detected also removable block devices at halt/reboot to be able
|
|
||||||
to flush data and send them the ATA standby command. This should
|
|
||||||
avoid data loss on USB sticks and other removable block devices.
|
|
||||||
* Flush block devices on halt/reboot if not done by the kernel.
|
|
||||||
* Set SHELL to /bin/sh in the environmant of shutdown.
|
|
||||||
* Retry to write out shutdown messages if interrupted.
|
|
||||||
* pidof/killall5 - make omit pid list a dynamic one.
|
|
||||||
* pidof - provide '-n' to skip stat(2) syscall on network based FS.
|
|
||||||
* init - avoid compiler warnings
|
|
||||||
* init - initialize console by using the macros from ttydefaults.h
|
|
||||||
* init - add the possiblity to ignore further interrupts from keyboard
|
|
||||||
* init - add the possiblity to set sane terminal line settings
|
|
||||||
* sulogin - add the possibility to reset the terminal io
|
|
||||||
* Fix some minor problems
|
|
||||||
* init - enable is_selinux_enabled() to detect selinuxfs
|
|
||||||
* Add fix for Debian bug #536574 -- Can be enabled by -DACCTON_OFF
|
|
||||||
* Add helper program fstab-decode to make it easier to handle
|
|
||||||
/etc/mtab content. Patch by Miloslav Trmac and Fedora.
|
|
||||||
* Add fix for Debian bug #335023 - Make sure TERM is set on FreeBSD.
|
|
||||||
* Add fix for Debian bug #374038 - Make it clear that shutdown -c can
|
|
||||||
only cancel a waiting shutdown, not an active one.
|
|
||||||
* Add note to pidof manual page about the use of readlink(2). Patch by
|
|
||||||
Bill Nottingham and Fedora.
|
|
||||||
* Add PAM patch contrib/notify-pam-dead.patch based on Debian bug
|
|
||||||
#68621, which will add PAM support for programs spawned by init on
|
|
||||||
the console like sulogin. Based on patch by Topi Miettinen. This
|
|
||||||
patch is not applied by default yet while we review its
|
|
||||||
usefullness. It is only helpful for session handling, as sulogin
|
|
||||||
do not use and will not use a PAM conv() function. The current
|
|
||||||
sulogin is able to handle DES as well as MD5, SHA, and Blowfish
|
|
||||||
encrypted passwords due using getpwnam(3).
|
|
||||||
* Move utmp/wtmp before the execvp() in spawn() to be sure to
|
|
||||||
use the correct pid even on a controlling tty
|
|
||||||
* Remaining problem is that the pid of the second fork() for
|
|
||||||
getting a controlling tty isn't that reported by spawn()
|
|
||||||
* Re-enable writting utmp/wtmp for boot scripts
|
|
||||||
* Extend sulogin to support additional encryption algorithms
|
|
||||||
* Re-enable maintenance message of sulogin
|
|
||||||
* Enable the sulogin fallback password check to handle MD5, SHA, and
|
|
||||||
Blowfish encrypted passwords in case of getpwnam(3) fails.
|
|
||||||
* sulogin picking the SELinux context was broken. Patch by Daniel Walsh
|
|
||||||
|
|
||||||
-------------------------------------------------------------------
|
-------------------------------------------------------------------
|
||||||
Fri Apr 9 14:30:08 CEST 2010 - werner@suse.de
|
Fri Apr 9 14:30:08 CEST 2010 - werner@suse.de
|
||||||
|
|
||||||
- Start the service sshd as early as possible (bnc#594223)
|
- Start the service sshd as early as possible (bnc#594223)
|
||||||
|
|
||||||
-------------------------------------------------------------------
|
|
||||||
Tue Mar 23 17:21:06 CET 2010 - werner@suse.de
|
|
||||||
|
|
||||||
- Test out sysvinit (2.88dsf) UNRELEASED; urgency=low
|
|
||||||
- Update to sysvinit (2.87dsf) world; urgency=low
|
|
||||||
|
|
||||||
* Document -e and -t options for telinit in init(8).
|
|
||||||
* Document in halt(8) that -n might not disable all syncing.
|
|
||||||
Patch by Bill Nottingham and Fedora
|
|
||||||
* Adjust output from "last -x". In reboot lines, print endpoint
|
|
||||||
of uptime too. In shutdown lines print downtimes rather than
|
|
||||||
the time between downs. Fix typo in string compare in last.c.
|
|
||||||
Patch by Thomas Hood.
|
|
||||||
* Improve handling of IPv6 addresses in last. Patch from Fedora.
|
|
||||||
* Add new option -F to last, to output full date string instead
|
|
||||||
of the short form provided by default. Patch from Olaf Dabrunz
|
|
||||||
and SuSe.
|
|
||||||
* Fix utmp/wtmp updating on 64-bit platforms. Patch by Bill
|
|
||||||
Nottingham and Fedora.
|
|
||||||
* Avoid unchecked return value from malloc() in utmpdump.
|
|
||||||
Patch from Christian 'Dr. Disk' Hechelmann and Fedora.
|
|
||||||
* Make sure to use execle and no execl when passing environment to
|
|
||||||
the new process. Patch from RedHat.
|
|
||||||
* Correct init to make sure the waiting status is preserved across
|
|
||||||
re-exec. Patch from RedHat.
|
|
||||||
* Correct init to avoid race condition when starting programs during
|
|
||||||
boot. Patch from SuSe.
|
|
||||||
* Allow 'telinit u' in runlevels 0 and 6. Patch from Thomas Hood.
|
|
||||||
* Improve error message from init if fork() fail. Patch found in Suse.
|
|
||||||
* Add support for SE Linux capability handling. Patch from Manoj
|
|
||||||
Srivastava, adjusted to avoid aborting if SE policy was loaded in
|
|
||||||
the initrd with patch from Bill Nottingham and Fedora.
|
|
||||||
* Add -c option to pidof for only matching processes with the same
|
|
||||||
process root. Ignore -c when not running as root. Patch from
|
|
||||||
Thomas Woerner and Fedora.
|
|
||||||
* Add usleep in killall5 after killing processes, to force the kernel
|
|
||||||
to reschedule. Patch from SuSe.
|
|
||||||
* Modify pidof to not print empty line if no pid was found.
|
|
||||||
* Modify init and sulogin to fix emergency mode's tty, making sure ^C
|
|
||||||
and ^Z work when booting with 'emergency' kernel option. Patch from
|
|
||||||
Samuel Thibault.
|
|
||||||
* Modify init to allow some time for failed opens to resolve themselves.
|
|
||||||
Patch from Bill Nottingham and Fedora.
|
|
||||||
* Modify init to shut down IDE, SCSI and SATA disks properly. Patches
|
|
||||||
from Sebastian Reichelt, Werner Fink and SuSe.
|
|
||||||
* Modify wall to use UT_LINESIZE from <utmp.h> instead of hardcoded
|
|
||||||
string lengths. Patch from SuSe.
|
|
||||||
* Change wall to make halt include hostname in output.
|
|
||||||
* Change killall to avoid killing init by mistake. Patch from SuSe.
|
|
||||||
* Change killall5 to use the exit value to report if it found any
|
|
||||||
processes to kill. Patch from Debian.
|
|
||||||
* Add option -o opmitpid to killall5, to make it possible to skip
|
|
||||||
some pids during shutdown. Based on patch from Colin Watson and
|
|
||||||
Ubuntu.
|
|
||||||
* Modify killall to work better with user space file system, by
|
|
||||||
changing cwd to /proc when stopping and killing processes, and
|
|
||||||
avoiding stat() when the value isn't used. Also, lock process
|
|
||||||
pages in memory to avoid paging when user processes are stopped.
|
|
||||||
Patch from Debian and Goswin von Brederlow with changes by Kel
|
|
||||||
Modderman.
|
|
||||||
* Change shutdown to only accept flags -H and -P with the -h flag,
|
|
||||||
and document this requirement in the manual page.
|
|
||||||
* Change reboot/halt to work properly when used as a login shell.
|
|
||||||
Patch by Dale R. Worley and Fedora.
|
|
||||||
* Let sulogin fall back to the staticly linked /bin/sash if both roots
|
|
||||||
shell and /bin/sh fail to execute.
|
|
||||||
|
|
||||||
-------------------------------------------------------------------
|
-------------------------------------------------------------------
|
||||||
Wed Mar 3 13:22:11 UTC 2010 - coolo@novell.com
|
Wed Mar 3 13:22:11 UTC 2010 - coolo@novell.com
|
||||||
|
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
#
|
#
|
||||||
# spec file for package sysvinit (Version 2.88)
|
# spec file for package sysvinit (Version 2.86)
|
||||||
#
|
#
|
||||||
# Copyright (c) 2010 SUSE LINUX Products GmbH, Nuernberg, Germany.
|
# Copyright (c) 2010 SUSE LINUX Products GmbH, Nuernberg, Germany.
|
||||||
#
|
#
|
||||||
@ -23,17 +23,17 @@ Name: sysvinit
|
|||||||
%define PDVER 2.0.2
|
%define PDVER 2.0.2
|
||||||
%define KPVER 2.16
|
%define KPVER 2.16
|
||||||
%define SCVER 1.10
|
%define SCVER 1.10
|
||||||
%define SIVER 2.88
|
%define SIVER 2.86
|
||||||
%define START 0.54
|
%define START 0.54
|
||||||
License: GPLv2+
|
License: GPLv2+
|
||||||
Group: System/Base
|
Group: System/Base
|
||||||
AutoReqProv: on
|
AutoReqProv: on
|
||||||
Version: 2.88
|
Version: 2.86
|
||||||
Release: 1
|
Release: 223
|
||||||
Summary: SysV-Style init
|
Summary: SysV-Style init
|
||||||
BuildRoot: %{_tmppath}/%{name}-%{version}-build
|
BuildRoot: %{_tmppath}/%{name}-%{version}-build
|
||||||
BuildRequires: audit-devel libselinux-devel libsepol-devel pam-devel
|
BuildRequires: libselinux-devel libsepol-devel
|
||||||
Source: http://download.savannah.gnu.org/releases/sysvinit/sysvinit-2.88dsf.tar.bz2
|
Source: sysvinit-2.86.tar.bz2
|
||||||
Source2: killproc-2.16.tar.bz2
|
Source2: killproc-2.16.tar.bz2
|
||||||
Source3: powerd-2.0.2.tar.bz2
|
Source3: powerd-2.0.2.tar.bz2
|
||||||
Source4: showconsole-1.10.tar.bz2
|
Source4: showconsole-1.10.tar.bz2
|
||||||
@ -43,16 +43,26 @@ Source7: sysvinit-rpmlintrc
|
|||||||
Source8: mkinitrd-boot.sh
|
Source8: mkinitrd-boot.sh
|
||||||
Source9: mkinitrd-kill1.sh
|
Source9: mkinitrd-kill1.sh
|
||||||
Source10: mkinitrd-kill2.sh
|
Source10: mkinitrd-kill2.sh
|
||||||
Patch: sysvinit-2.88dsf.dif
|
Patch: sysvinit-2.86.dif
|
||||||
Patch1: sysvinit-2.82-startstop.patch
|
Patch1: sysvinit-2.86-nfs4pidof.patch
|
||||||
Patch2: sysvinit-2.88dsf-suse.patch
|
Patch2: powerd-2.0.2.dif
|
||||||
Patch3: sysvinit-2.88dsf-no-kill.patch
|
Patch3: killproc-2.16.dif
|
||||||
Patch4: notify-pam-dead.patch
|
Patch5: sysvinit-2.86-sulogin.patch
|
||||||
Patch5: sysvinit-last-ipv6-heuristic.patch
|
Patch6: sysvinit-2.82-startstop.patch
|
||||||
Patch20: powerd-2.0.2.dif
|
Patch7: sysvinit-2.85-suse.patch
|
||||||
Patch30: killproc-2.16.dif
|
Patch8: sysvinit-2.85-paths.patch
|
||||||
Patch40: showconsole-1.10.dif
|
Patch9: sysvinit-2.86-utmp.patch
|
||||||
Patch50: startpar-0.54.dif
|
Patch10: showconsole-1.10.dif
|
||||||
|
Patch11: sysvinit-2.86-race.patch
|
||||||
|
Patch12: sysvinit-2.86-lib64.patch
|
||||||
|
Patch13: sysvinit-2.82-multiline.patch
|
||||||
|
Patch14: startpar-0.54.dif
|
||||||
|
Patch15: sysvinit-2.86-usage-message.patch
|
||||||
|
Patch16: sysvinit-2.86-full-time.patch
|
||||||
|
Patch17: sysvinit-2.86-hddown.patch
|
||||||
|
Patch18: sysvinit-2.86-selinux.patch
|
||||||
|
Patch19: sysvinit-2.86-fuse-no-kill.patch
|
||||||
|
Patch20: sysvinit-2.86-mdmon-no-kill.patch
|
||||||
Requires: sysvinit-tools
|
Requires: sysvinit-tools
|
||||||
Provides: sbin_init
|
Provides: sbin_init
|
||||||
|
|
||||||
@ -74,7 +84,7 @@ Group: System/Base
|
|||||||
Requires(preun): coreutils mkinitrd %insserv_prereq
|
Requires(preun): coreutils mkinitrd %insserv_prereq
|
||||||
Requires(postun): coreutils mkinitrd %insserv_prereq
|
Requires(postun): coreutils mkinitrd %insserv_prereq
|
||||||
%else
|
%else
|
||||||
PreReq: coreutils mkinitrd %insserv_prereq
|
PreReq: coreutils mkinitrd %insserv_prereq
|
||||||
%endif
|
%endif
|
||||||
|
|
||||||
%description tools
|
%description tools
|
||||||
@ -83,34 +93,45 @@ to startpar, killproc and pidof. System V init specific programs are in the
|
|||||||
sysvinit package.
|
sysvinit package.
|
||||||
|
|
||||||
%prep
|
%prep
|
||||||
%setup -n sysvinit-%{SIVER}dsf -q -b 2 -b 3 -b 4 -b 5
|
%setup -q -b 2 -b 3 -b 4 -b 5
|
||||||
%patch1 -p0 -b .startstop
|
%patch -P 1 -b .nfs4pidof
|
||||||
%patch2 -p0 -b .suse
|
%patch -P 5 -b .sulogin
|
||||||
%patch3 -p0 -b .no-kill
|
%patch -P 6 -b .ststdmn
|
||||||
%patch4 -p0 -b .pam
|
%patch -P 7 -b .suse
|
||||||
%patch5 -p2 -b .ipv6
|
%patch -P 8 -b .paths
|
||||||
|
%patch -P 9 -b .utmp
|
||||||
|
%patch -P 11 -b .race
|
||||||
|
%patch -P 12 -b .lib64
|
||||||
|
%patch -P 13 -b .multiline
|
||||||
|
%patch -P 15 -b .usage
|
||||||
|
%patch -P 16 -b .fulltime
|
||||||
|
%patch -P 17 -b .hddown
|
||||||
|
%patch -P 18 -b .selinux
|
||||||
|
%patch -P 19 -b .fuse
|
||||||
|
%patch -P 20 -b .mdmon
|
||||||
%patch
|
%patch
|
||||||
pushd ../powerd-%{PDVER}
|
pushd ../powerd-%{PDVER}
|
||||||
%patch20
|
%patch -P 2
|
||||||
popd
|
popd
|
||||||
pushd ../killproc-%{KPVER}
|
pushd ../killproc-%{KPVER}
|
||||||
%patch30
|
%patch -P 3
|
||||||
popd
|
popd
|
||||||
pushd ../showconsole-%{SCVER}
|
pushd ../showconsole-%{SCVER}
|
||||||
%patch40
|
%patch -P 10
|
||||||
popd
|
popd
|
||||||
pushd ../startpar-%{START}
|
pushd ../startpar-%{START}
|
||||||
%patch50
|
%patch -P 14
|
||||||
popd
|
popd
|
||||||
%_fixowner .
|
%_fixowner .
|
||||||
%_fixgroup .
|
%_fixgroup .
|
||||||
/bin/chmod -Rf a+rX,g-w,o-w .
|
/bin/chmod -Rf a+rX,g-w,o-w .
|
||||||
|
|
||||||
%build
|
%build
|
||||||
RPM_OPT_FLAGS="${RPM_OPT_FLAGS} -D_FILE_OFFSET_BITS=64 -pipe"
|
RPM_OPT_FLAGS="${RPM_OPT_FLAGS} -D_FILE_OFFSET_BITS=64"
|
||||||
|
export RPM_OPT_FLAGS
|
||||||
|
CFLAGS="-Wall ${RPM_OPT_FLAGS} -D_GNU_SOURCE -D__NO_STRING_INLINES -pipe"
|
||||||
CC=gcc
|
CC=gcc
|
||||||
export RPM_OPT_FLAGS CC
|
make %{?jobs:-j%jobs} -C src CFLAGS="$CFLAGS" CC="$CC"
|
||||||
make %{?_smp_mflags} WITH_SELINUX=yes DISTRO=SuSE
|
|
||||||
pushd ../showconsole-%{SCVER}
|
pushd ../showconsole-%{SCVER}
|
||||||
make %{?_smp_mflags}
|
make %{?_smp_mflags}
|
||||||
popd
|
popd
|
||||||
@ -122,7 +143,7 @@ pushd ../powerd-%{PDVER}
|
|||||||
./configure --prefix= --bindir='$(DESTDIR)/sbin' \
|
./configure --prefix= --bindir='$(DESTDIR)/sbin' \
|
||||||
--mandir='$(DESTDIR)%{_mandir}' \
|
--mandir='$(DESTDIR)%{_mandir}' \
|
||||||
--sbindir='$(DESTDIR)/sbin'
|
--sbindir='$(DESTDIR)/sbin'
|
||||||
make %{?_smp_mflags} CFLAGS="-I../sysvinit-%{SIVER}dsf/src $RPM_OPT_FLAGS "
|
make %{?_smp_mflags} CFLAGS="-I../sysvinit-%{version}/src $CFLAGS"
|
||||||
%endif
|
%endif
|
||||||
popd
|
popd
|
||||||
pushd ../startpar-%{START}
|
pushd ../startpar-%{START}
|
||||||
@ -141,7 +162,7 @@ popd
|
|||||||
mkdir -m 755 -p ${RPM_BUILD_ROOT}%{_mandir}/man1
|
mkdir -m 755 -p ${RPM_BUILD_ROOT}%{_mandir}/man1
|
||||||
mkdir -m 755 -p ${RPM_BUILD_ROOT}%{_mandir}/man5
|
mkdir -m 755 -p ${RPM_BUILD_ROOT}%{_mandir}/man5
|
||||||
mkdir -m 755 -p ${RPM_BUILD_ROOT}%{_mandir}/man8
|
mkdir -m 755 -p ${RPM_BUILD_ROOT}%{_mandir}/man8
|
||||||
make install -C src MANPATH=%{_mandir} ROOT=${RPM_BUILD_ROOT} WITH_SELINUX=yes DISTRO=SuSE
|
make install -C src MANPATH=%{_mandir} ROOT=${RPM_BUILD_ROOT}
|
||||||
test -p ${RPM_BUILD_ROOT}/dev/initctl || {
|
test -p ${RPM_BUILD_ROOT}/dev/initctl || {
|
||||||
rm -f ${RPM_BUILD_ROOT}/dev/initctl
|
rm -f ${RPM_BUILD_ROOT}/dev/initctl
|
||||||
mknod ${RPM_BUILD_ROOT}/dev/initctl p
|
mknod ${RPM_BUILD_ROOT}/dev/initctl p
|
||||||
@ -216,7 +237,6 @@ rm -rf ${RPM_BUILD_ROOT}
|
|||||||
|
|
||||||
%files
|
%files
|
||||||
%defattr (-,root,root,755)
|
%defattr (-,root,root,755)
|
||||||
%config /etc/pam.d/init
|
|
||||||
/sbin/halt
|
/sbin/halt
|
||||||
/sbin/init
|
/sbin/init
|
||||||
/sbin/poweroff
|
/sbin/poweroff
|
||||||
@ -262,7 +282,6 @@ rm -rf ${RPM_BUILD_ROOT}
|
|||||||
# /sbin/intr
|
# /sbin/intr
|
||||||
/sbin/blogger
|
/sbin/blogger
|
||||||
/sbin/blogd
|
/sbin/blogd
|
||||||
/sbin/fstab-decode
|
|
||||||
/sbin/showconsole
|
/sbin/showconsole
|
||||||
/sbin/setconsole
|
/sbin/setconsole
|
||||||
/sbin/isserial
|
/sbin/isserial
|
||||||
@ -285,14 +304,16 @@ rm -rf ${RPM_BUILD_ROOT}
|
|||||||
%doc %{_mandir}/man1/lastb.1.gz
|
%doc %{_mandir}/man1/lastb.1.gz
|
||||||
%doc %{_mandir}/man1/usleep.1.gz
|
%doc %{_mandir}/man1/usleep.1.gz
|
||||||
%doc %{_mandir}/man1/fsync.1.gz
|
%doc %{_mandir}/man1/fsync.1.gz
|
||||||
|
%ifnarch s390 s390x
|
||||||
|
%doc %{_mandir}/man8/powerd.8.gz
|
||||||
|
%doc %{_mandir}/man8/detectups.8.gz
|
||||||
|
%endif
|
||||||
# /usr/include/libblogger.h
|
# /usr/include/libblogger.h
|
||||||
# /usr/lib/libblogger.a
|
# /usr/lib/libblogger.a
|
||||||
%doc %{_mandir}/man1/mountpoint.1.gz
|
%doc %{_mandir}/man1/mountpoint.1.gz
|
||||||
%doc %{_mandir}/man1/utmpdump.1.gz
|
|
||||||
# %doc %{_mandir}/man8/bootlogd.8.gz
|
# %doc %{_mandir}/man8/bootlogd.8.gz
|
||||||
%doc %{_mandir}/man8/blogger.8.gz
|
%doc %{_mandir}/man8/blogger.8.gz
|
||||||
%doc %{_mandir}/man8/blogd.8.gz
|
%doc %{_mandir}/man8/blogd.8.gz
|
||||||
%doc %{_mandir}/man8/fstab-decode.8.gz
|
|
||||||
%doc %{_mandir}/man8/showconsole.8.gz
|
%doc %{_mandir}/man8/showconsole.8.gz
|
||||||
%doc %{_mandir}/man8/setconsole.8.gz
|
%doc %{_mandir}/man8/setconsole.8.gz
|
||||||
%doc %{_mandir}/man8/isserial.8.gz
|
%doc %{_mandir}/man8/isserial.8.gz
|
||||||
@ -302,10 +323,6 @@ rm -rf ${RPM_BUILD_ROOT}
|
|||||||
%doc %{_mandir}/man8/killall5.8.gz
|
%doc %{_mandir}/man8/killall5.8.gz
|
||||||
%doc %{_mandir}/man8/killproc.8.gz
|
%doc %{_mandir}/man8/killproc.8.gz
|
||||||
%doc %{_mandir}/man8/pidof.8.gz
|
%doc %{_mandir}/man8/pidof.8.gz
|
||||||
%ifnarch s390 s390x
|
|
||||||
%doc %{_mandir}/man8/powerd.8.gz
|
|
||||||
%doc %{_mandir}/man8/detectups.8.gz
|
|
||||||
%endif
|
|
||||||
%doc %{_mandir}/man8/startproc.8.gz
|
%doc %{_mandir}/man8/startproc.8.gz
|
||||||
%doc %{_mandir}/man8/start_daemon.8.gz
|
%doc %{_mandir}/man8/start_daemon.8.gz
|
||||||
%doc %{_mandir}/man8/startpar.8.gz
|
%doc %{_mandir}/man8/startpar.8.gz
|
||||||
|
Loading…
Reference in New Issue
Block a user