[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: raw kbd device in oskit-mach
Re: raw kbd device in oskit-mach
Tue, 5 Mar 2002 19:51:02 -0500 (EST)
> currently, what I am doing for the raw kbd access in oskit-mach,
> is to unconditionally open the direct console in a ds_direct_console_stream,
> which might be identical to ds_console_stream if you don't use a serial
> console to boot with.
I am assuming you mean both variables get the same pointer. I don't think
calling cq_direct_console_init more than once will work at all, because
oskit_osenv_irq_alloc will fail the second time.
> My idea was to disable raw mode on a no senders notification. Problem
> is, I can not really distinguish between "console" and "kbd" in the
> no-serial- console-at-boot case.
The simplest thing to do is whip up a dummy COM object that exists just to
notice when it's dying and diddle the state then. The object needs nothing
but struct oskit_iunknown_ops * and a reference count. Just have its query
call return ds_console_stream (after doing addref on it). The
addref/release calls on your little object just maintain the ref count,
and when it goes to zero you have "last kbd close" and do your thing.
> For development, it would be nicer if I could "grab" the keyboard when
> opening "kbd", but I am not sure that this is feasible. It would be nice
> to interrupt all pending reads, or at least make all future reads from
> the "console" block until "kbd" is closed. Is that feasible?
You could hack this up at the Mach level. You'd need to grab the other
device_t and look at its ->com.stream. If there is anything on its
.read_queue, then you need to take it off and diddle the bits/listener as
ds_asyncio_ready does. You can either finish off those requests with an
error reply to interrupt them, or you can just stash the queue and restore
it later to constitute blocking those requests until you switch back.
(Blocking seems like the better behavior, but it is a bit more hassle to do.)
You could then hack ds_asyncio_read_inband to check some flag you set in
the device_t and thread_block on something you will thread_wakeup when you
clar the flag. That is inefficient but probably easy. Better would be to
have ds_asyncio_read_inband when seeing that flag always just queue an
asynchronous request but not add the listener. Then when switching back,
you check for requests and install the listener as appropriate.
But it probably behaves more properly to do this at the oskit level
instead. That is, have two separate input queues (i.e., do indeed call
cq_direct_console_init twice). The reason for this is that once you have
the console open in translated mode, but there are no readers, then
anything typed will be translated and queued as ASCII bytes. Switching
modes and then reading from this same queue would give bytes that are
garbage as raw scan codes. Likewise, when you had been in raw mode but
there are no readers now, anything typed will be queued as raw scan codes.
Switching back to translated mode and then reading from this queue would
give garbage ASCII bytes. Separate queues just saves the type-ahead for
each mode until the switch is done. Actually, it probably makes more sense
just to flush the input queue on switching. (If you were to have two
separate queueing COM streams, the way to do that would be to whip up an
interposing osenv_irq COM object or two that catches the right pointers
passing through so that you can later deinstall the one's irq handler and
install the other's when switching.)
But I am just mentioning some ideas for you to think about. I don't think
that latter is worth the effort. Perhaps we should just go straight to
figuring out what we want the minimal console device to do in the long-run,
when real drivers and user-level code replace it except for emergencies.
I think it should be a special device, rather than just an open-time hook
for underlying things. I'm thinking that the console device would not
actually set up anything at all for input until it gets the first
device_read call. In normal Hurd operation, it will never get one. The
Hurd will boot and start up user-level servers talking to specific
keyboard/serial devices. In the emergency boot situation (prompts from
init et al), the console reads will be happening before any real input
devices have been opened. We'll need some sort of hack for when a real
keyboard device is first opened, to tear down the console input stuff.
There really should never be any more reads from the minimal console device
after a real input device has been used. If there are, we might want to
consider it a catastrophic emergency situation and forcibly steal the IRQ
from the other driver (which will then presumably just be scrod and maybe
could not be used again).