I'm counting my threads, one, two, three, four, five... [1]

Poul-Henning Kamp phk at phk.freebsd.dk
Fri Sep 24 02:01:08 PDT 2004


I've completed my sweep of the kernel and I belive that we now have a
reliable count of the number of threads currently inside any particular
cdev and consequently, with a bit of adding up, also for each cdevsw.

There are two soft spots marked with XXX (devfs_rule and vm_mmap)
and one big hack, snp(4).

The next step is to add a new method to the cdevsw which purges threads
from the driver.  The best name I can come up with is d_evict().  The
drivers should make this function wakeup(9) on anything a thread could
be sleeping on for the relevant cdev and the tread on waking up should
examine whatever bits it can, realize the hw/driver/whatever is gone
and exit the driver with ENXIO error return.

If this cdevsw method is present, destroy_dev() will use it and will
sleep until all threads have cleared out.

So for a typical driver things will look like this:

foo_evict(struct cdev *dev)
{
	struct foo_sc *sc;

	/* XXX: NB: no locks, only wakeups */
	sc = dev->si_drv1;
	wakeup(sc->bing);
	wakeup(sc->bongle);
	wakeup(sc->bang);
}

foo_detach(dev)
{
	...

	sc->flags |= GONE;
	destroy_dev(sc->cdev);
	/* XXX: we now know there are no threads involved with this cdev */
	...
}

destroy_dev() will work more or less this way:


	...
	dev_lock();
	csw = cdev->si_devsw;
	cdev->si_devsw = NULL
	while (csw->d_evict != NULL && cdev->si_threacount > 0) {
		(csw->d_evict)(cdev);
		msleep(&dev_lock, ..., hz/10);
	}
	dev_unlock();
	...

I will also add a convenience function called destroy_cdevsw() which
will call destroy_dev() on all cdevs using the cdevsw in question.

I belive this gives us the handle we need to unload drivers and remove
hardware without panicing in the lower layers of the kernel.  The
higher layers may still have a thing or two to learn in this respect.

Poul-Henning

[1]  It used to be possible to legally download the D:A:D tune which
inspired the subject, but I can't find the link anymore, sorry :-(

-- 
Poul-Henning Kamp       | UNIX since Zilog Zeus 3.20
phk at FreeBSD.ORG         | TCP/IP since RFC 956
FreeBSD committer       | BSD since 4.3-tahoe    
Never attribute to malice what can adequately be explained by incompetence.


More information about the freebsd-arch mailing list