Re-implement select() for channels

The major things to overcome in this implementation were to prevent spurious
wakeups during upgrading, and be sure to go to sleep on the proper port during
selection (taking into account pending upgrades).

The interface to Select has been tweaked, and it's about as bad as it was
before, and just as slow as it was before.

This does re-implement some portions of channels, but they're mostly just small
portions that are trivial rewrites.