Pending patches

Rob Landley rob at landley.net
Mon Nov 10 11:17:26 PST 2008


On Monday 10 November 2008 06:11:16 Vladimir Dronnikov wrote:
> > reboot -f
> > echo "Kernel has been instructed to reboot"
> > while true; do sleep 9999; done
> >
> > because otherwise, if script exits, runsvdir
> > will loop back and restart services, and this is definitely
> > what you dont want to happen!
>
> Wonder what happens when init dies and kernel oopses? Does kernel
> sync/umount filesystems?

Nope, it's a normal oops.

The kernel's theory on oopses is that the system is no longer in a good state, 
so it should stop writing to the disk _now_ because it may be writing 
garbage.

(However, this doesn't apply to network access, so it continues to route 
packets.  A common trick years ago was to set up your routing tables and then 
have PID 1 exit so the kernel paniced, because the paniced kernel would 
continue to route packets with _no_userspace_running_.  Darn hard to hack a 
system like that.)

> If so I'd let it be. 
> Wonder also does kernel sync/umount filesystems when one issues
> reboot(whatever)?

Nope, that's up to userspace to do.

> I still view some awkwardness in the procedure. You treat init as perpetuum
> mobile of which we have to break a detail to get it stopped. I mostly tend
> to treat it as a process that just exits when your system have accomplished
> its task. Where am I wrong, Denys?

You're wrong in that the kernel guys have defined init as a special process 
that panics the kernel if it exits.  This has been true for Linux for 18 
years, and was true of other Unixes before that.

PID 1 is special, in lots of little ways.  It's the default reaper of zombie 
processes whose parents have exited.  It's the default target of signals for 
processes that don't otherwise have a parent (such as anything that's called 
daemonize()).  Various system things that must belong to a userspace process 
get attached to init because it's guaranteed to be there.  (Back before we 
had so many kernel threads, interrupt routines that needed a process context 
would borrow PID 1's.  These days, those new kernel threads have init as 
their parent.)

Internally, the kernel has a variable "init_task" statically referencing PID 
1's context, which is used by things like daemonize() (the kernel internal 
version in kernel/exit.c; I'm actually indirectly responsible for Andrew 
Morton creating that sucker long ago: 
http://lkml.indiana.edu/hypermail/linux/kernel/0105.0/0045.html).  There are 
also a couple of different "task_reparent_to_init()" functions in the 
security subdirectory. 

On a design level, the purpose of the kernel is to run userspace.  The kernel 
launches one task by hand, and then that task is in charge of the system from 
then on.  If that task ever exits, the kernel doesn't know what it's supposed 
to be doing anymore, at a design level.  It was decreed back in the 1970's 
that PID 1 _should_not_exit_, and unix has gone along with that ever since

As for standards on this, see SUSv3 section 4.12, reserving PID 1 for the 
system:
http://www.opengroup.org/onlinepubs/000095399/

See the definition of _exit(), which says:
http://www.opengroup.org/onlinepubs/000095399/functions/_exit.html
  The parent process ID of all of the calling process' existing child
  processes and zombie processes shall be set to the process ID of an
  implementation-defined system process. That is, these processes shall be
  inherited by a special system process.

  (How you're supposed to do that if the special system process is the one
  exiting is left as an exercise for the reader.)

The definition of kill() says:
  http://www.opengroup.org/onlinepubs/000095399/functions/kill.html

  The unspecified processes to which a signal cannot be sent may include the
  scheduler or init.

Keep in mind that this standard tried to be so vague that it could allow 
Windows NT and IBM's System 360 to be specified as Posix compliant...

Rob


More information about the busybox mailing list