DragonFly submit List (threaded) for 2007-06
DragonFly BSD
DragonFly submit List (threaded) for 2007-06
[Date Prev][Date Next]  [Thread Prev][Thread Next]  [Date Index][Thread Index]

Re: rough-draft VKERNEL host-initiated shutdown patch


From: Matthew Dillon <dillon@xxxxxxxxxxxxxxxxxxxx>
Date: Tue, 12 Jun 2007 11:09:35 -0700 (PDT)

:If the special thread doesn't need to do any other cleanup that I'm
:likely unaware of, I can give it another shot this weekend.
:
:Not yet knowing the overall code paths unfortunately means I'm
:kind of coding this blind .. but I suppose the point is to learn as I go.
:
:I assume the reason for the thread is that the way things are currently
:called, the VK might not be in a consistent internal state when the
:signal is delivered to init and/or init is rescheduled to run?

    Right.  The idle loop isn't allowed to block, and the shutdown
    sequence involves a lot of blocking.  The go-user code is in a
    sane state and it would be ok to block there, but we wouldn't
    get consistent checks.

:to clarify:
:
: - keep signal handler and shutdown function in the exception setup
: - create kthread somewhere ( main() ? platform init? )
: - remove checks from both idle loop / task switching areas
: - add check / wakeup logic to signalmailbox()
:
:Thanks,
:
:- Chris

    I think the platform init code is too early.   The memory subsystem
    isn't really initialized until it gets into the middle mi_startup().

    What I recommend is that you create a SYSINIT in
    platform/vkernel/i38/exception.c with a priority of SI_BOOT2_MACHDEP
    to create the thread.  This looks kinda messy, but it should work.

    static void
    sigshutdown_daemon(void)
    {
	while (mdcpu->gd_shutdown == 0)
		tsleep(&mdcpu->gd_shutdown, 0, "sswait", 0);
	}
	mdcpu->gd_shutdown = 0;
	kprintf("Caught SIGTERM from host system. Shutting down...\n");
	if (initproc != NULL) {
		ksignal(initproc, SIGUSR2);
	} else {
		reboot(RB_POWEROFF);
	}
    }

    static struct thread *sigshutdown_thread;

    static struct kproc_desc sigshut_kp = {
	"sigshutdown", sigshutdown_daemon, &sigshutdown_thread
    };

    SYSINIT(sigshutdown, SI_BOOT2_MACHDEP, SI_ORDER_ANY,
	    kproc_start, &sigshut_kp);


    Then put a check in signalmbox which wakes up the thread:

    /*
     * we only need to wake up our shutdown thread once.  Keep it non-zero
     * so the shutdown thread can detect it.
     */
    if (mdcpu->gd_shutdown > 0) {
	mdcpu->gd_shutdown = -1;
	wakeup(&mdcpu->gd_shutdown);
    }

					-Matt
					Matthew Dillon 
					<dillon@backplane.com>



[Date Prev][Date Next]  [Thread Prev][Thread Next]  [Date Index][Thread Index]