Hi,
Today I am blessed with the gift of time travel..
Najimac wrote:I have the first layer ready, I am not worried about that (It is not that hard).
So I can implement the message as a struct with a character and the key state, And then
I listen for it, But wouldn't checking every possible key be slow.
Brendan wrote:The second thing is that you need some way to transfer "key presses" (not characters, as there are no character to represent "F1 key" or "pause key" or "insert key") to something else (e.g. from the IRQ handler to the other half of the keyboard driver, or from the keyboard driver to a GUI or virtual terminal layer or something). This is typically a 2 part problem - transferring the data itself, plus some way to arrange for the receiver to get CPU time.
Transferring the data itself can be (e.g.) pushing the parameters for a function call on the stack, or storing a message in memory (in a queue?) somewhere. Arranging for the receiver to get CPU time can be actually calling the function after the parameters are stored (the "call" instruction), or telling the scheduler to unblock the task that received the message.
If you only do half (transfer the data but don't arrange for the receiver to get CPU time) then it ends up broken. A polling loop (e.g. constantly checking if a message was received) is one of the consequences of failing to do things properly (e.g. not being able to tell the scheduler, "don't give me any CPU time until a message is received").
Najimac wrote:But translating the character once it's received be simpler?
I mean like stacked based communication would be a bit faster but I am not sure how well it will turn out.
Brendan wrote:For example; you might implement all the layers within the IRQ handler (which is probably a bad idea - you should do the least work possible in an IRQ handler) and in that case almost all of the places I've said "sent" (all except the last) could be a function call.
The reason it's bad is other more important IRQs can be waiting while you're doing less important work; which results in poor IRQ latency (time between IRQ occurring and being serviced) and worse performance. Note the "(all except the last)" - a keyboard driver that directly calls a function within (e.g.) a GUI would be completely insane. This implies that you must implement something and can't just use function calls for everything.
Najimac wrote:But how would I know if this is the last byte, That depends on the current usage of the keyboard input (Like wait until newline is pressed?).
If you look at the scan code table (for whichever scan code set you're using) you'll see that most multi-byte scan codes begin with a special "escape code" byte and are followed by a second byte. You only need a small state machine to keep track of which special escape code bytes have been received.
For example:
Code: Select all
byte = in(0x60);
keycode = 0;
switch(state) {
case 0:
if(byte == ESCAPE_CODE1) {
state = 1;
} else {
// last byte of a 1-byte scancode!
keycode = byte;
}
break;
case 1:
// last byte of a 2-byte scancode!
keycode = byte + 0x100;
break;
}
if(keycode != 0) {
// Got a full keycode!
send_to_next_layer(keycode);
}
For some keys (pause/break) the multi-byte sequence is larger, but you just add more states to the state machine to cover that.
Najimac wrote:I think a microkernel will be a bit harder to implement, I am not focusing on anything but keyboard input, I cannot implement ipc right now.
Brendan wrote:Note that in my opinion it's a mistake to begin writing any device driver before "communication between things" (
IPC) is implemented and tested.
This has nothing to do with micro-kernels. The "deferred procedure calls" and the "kernel tasklets" are both intended for monolithic kernels. Things like messages and pipes are also implemented in virtually all monolithic kernels.
Mostly; this is a bit like waking up and going shopping. You might get to the shops, and you might choose the items you want to purchase; but you still won't be able to buy anything because you're naked. If you actually want to do shopping successfully; you have to wake up, get dressed, and then go shopping. You can't repeatedly say "I don't want to get dressed" (or "I don't want to implement IPC") and the get all confused when you fail.
Cheers,
Brendan