#include <const.h>
#include <arch/i386.h>
#include <arch/interrupt.h>
#include <kernel/console.h>
#include <kernel/kernel.h>
#include <kernel/queue.h>
#include <kernel/semaphore.h>
#include <kernel/speaker.h>
#include <kernel/task.h>
#include <kernel/keyboard.h>
Go to the source code of this file.
Functions | |
| void | keyb_wait () |
| Wait after a keyboard operation. | |
| void | update_leds () |
| Update keyboard leds. | |
| word | scan_key () |
Get the hitten key keyboard code.
| |
| void | keyboard_handler () |
| This is the keyboard interrupt handler routine. It is invoked every time a key is pressed or released on the keyboard. | |
| void | init_keyboard () |
| Initialize the low-level keyboard driver. | |
| int | kgetchar () |
Wait for keypressed and return the hitten character ASCII code.
| |
| int | keyb_read () |
Return the first key in the buffer, without waiting if the buffer is empty.
| |
Variables | |
| word | regular [128] |
| US keyboard keymap :: regular keys. | |
| word | with_shift [128] |
| US keyboard keymap :: "with SHIFT" keys. | |
| word | with_alt [128] |
| US keyboard keymap :: "with ALT" keys. | |
| word | with_control [128] |
| US keyboard keymap :: "with CTRL" keys. | |
| byte | keypad_char [] = {'7','8','9','-','4','5','6','+','1','2','3','0','.'} |
| The keypad map. | |
| byte | shift = 0 |
| SHIFT flag. | |
| byte | ctrl = 0 |
| CTRL flag. | |
| byte | alt = 0 |
| ALT flag. | |
| queue_t * | keyb_queue = NULL |
| Queue for the task that are waiting for the keyboard. | |
Definition in file keyboard.c.
|
|
Initialize the low-level keyboard driver.
Definition at line 280 of file keyboard.c.
00281 {
00282 // Install the keyboard handler //
00283 install_irq_handler( KEYBOARD_IRQ, (void *)&keyboard_handler );
00284
00285 // Set typematic delay as short as possible //
00286 outportb(KEYB_PORT, KEYB_SET_TYPEMATIC);
00287 keyb_wait();
00288 // typematic 0 means "MODE CON RATE=30 DELAY=1" //
00289 outportb(KEYB_PORT, 0);
00290
00291 // Initialize leds //
00292 update_leds();
00293 }
|
|
|
Return the first key in the buffer, without waiting if the buffer is empty.
Definition at line 341 of file keyboard.c.
00342 {
00343 console_t *cons = get_console_addr( get_curr_task()->console );
00344 word key;
00345 dword IF = GET_IF();
00346
00347 // If the task's console is not the current console return //
00348 while ( get_curr_task()->console != get_curr_console() )
00349 return(NULL);
00350
00351 // If the keyboard buffer is empty return NULL //
00352 if (cons->keyb_buf_count==0) return(NULL);
00353
00354 disable();
00355
00356 // Update keyboard buffer in mutual exclusion //
00357 (cons->keyb_buf_count)--;
00358 if ( ++(cons->keyb_buf_read) >= KEYB_BUF_DIM )
00359 cons->keyb_buf_read = 0;
00360 key = cons->keyb_buffer[cons->keyb_buf_read];
00361
00362 SET_IF(IF);
00363
00364 return(key);
00365 }
|
|
|
Wait after a keyboard operation.
Definition at line 90 of file keyboard.c.
00091 {
00092 uint32_t retries=500000L;
00093
00094 while (((inportb(KEYB_STATUS) & KEYB_BUSY) == KEYB_BUSY) && retries!=0)
00095 {
00096 retries--;
00097 }
00098 }
|
|
|
This is the keyboard interrupt handler routine. It is invoked every time a key is pressed or released on the keyboard.
Definition at line 145 of file keyboard.c.
00146 {
00147 task_t *p;
00148 int console, count;
00149 // Current console structure.
00150 console_t *curr_cons = get_console_addr( get_curr_console() );
00151 // Key hitten ASCII code.
00152 word code;
00153 // Key hitten keyboard code.
00154 word keypressed = scan_key();
00155
00156 // If CTRL+ALT+Canc => Reboot the system... //
00157 if (ctrl==1 && alt==1 && keypressed==DEL_SCAN) reboot();
00158
00159 if (alt==1) code = with_alt[keypressed];
00160 else if (ctrl==1) code = with_control[keypressed];
00161 else
00162 {
00163 if (curr_cons->caps_lock==0 && shift==0) code = regular[keypressed];
00164 else if (curr_cons->caps_lock==0 && shift==1) code = with_shift[keypressed];
00165 else if (curr_cons->caps_lock==1 && shift==0)
00166 {
00167 code = regular[keypressed];
00168 if (((code&0xFF)>='a') && ((code&0xFF)<='z')) code-='a'-'A';
00169 }
00170 else
00171 {
00172 code = with_shift[keypressed];
00173 if (((code&0xFF)>='A') && ((code&0xFF)<='Z')) code+='a'-'A';
00174 }
00175 if ((curr_cons->num_lock!=shift) && (keypressed>=71 && keypressed<=83))
00176 code = keypad_char[keypressed-71];
00177 }
00178
00179 // Print the char only if it's not released (bit 8 set) //
00180 switch (keypressed)
00181 {
00182 case 42: // LShift
00183 shift=1;
00184 break;
00185
00186 case (42+128):
00187 shift=0;
00188 break;
00189
00190 case 54: // RShift
00191 shift=1;
00192 break;
00193
00194 case (54+128):
00195 shift=0;
00196 break;
00197
00198 case 56: // ALT
00199 alt=1;
00200 break;
00201
00202 case (56+128):
00203 alt=0;
00204 break;
00205
00206 case 29: // CTRL
00207 ctrl=1;
00208 break;
00209
00210 case (29+128):
00211 ctrl=0;
00212 break;
00213
00214 case 58: // CAPS LOCK
00215 curr_cons->caps_lock ^= 1;
00216 update_leds();
00217 break;
00218
00219 case 69: // NUM LOCK
00220 curr_cons->num_lock ^= 1;
00221 update_leds();
00222 break;
00223
00224 case 70: // SCROLL LOCK
00225 curr_cons->scroll_lock ^= 1;
00226 update_leds();
00227 break;
00228
00229 case 0xE1: // PAUSE
00230 // Wait until released... //
00231 while (scan_key() != 0xC5);
00232 break;
00233
00234 default:
00235
00236 // Update keyboard buffer. This is an interrupt //
00237 // handler so we are already in mutual exclusion!!! //
00238
00239 if (!(keypressed & 0x80))
00240 {
00241 if ( (code>=ALT_F1) && (code<=ALT_F10) )
00242 {
00243 // Change console //
00244 console = ((code-ALT_F1) >> 8) + 1;
00245 switch_to_console( console );
00246
00247 // Every task in the selected console
00248 // need to wake-up.
00249 count = count_queue( &keyb_queue );
00250 for ( ; count; --count )
00251 {
00252 p = pick_queue( &keyb_queue );
00253 if ( p->console==console )
00254 {
00255 wakeup_task( p );
00256 rem_queue( &keyb_queue, p );
00257 }
00258 }
00259 return;
00260 }
00261 // A key has been released => update the buffer //
00262 if ( (curr_cons->keyb_buf_count) < KEYB_BUF_DIM )
00263 {
00264 (curr_cons->keyb_buf_count)++;
00265 if ( ++(curr_cons->keyb_buf_write) >= KEYB_BUF_DIM )
00266 curr_cons->keyb_buf_write = 0;
00267 curr_cons->keyb_buffer[curr_cons->keyb_buf_write] = code;
00268 }
00269 else
00270 {
00271 // Buffer full => beep! //
00272 beep();
00273 }
00274 }
00275 break;
00276 }
00277 }
|
|
|
Wait for keypressed and return the hitten character ASCII code.
Definition at line 298 of file keyboard.c.
00299 {
00300 task_t *ct = get_curr_task();
00301 console_t *cons = get_console_addr( ct->console );
00302 word key;
00303 uint32_t IF = GET_IF();
00304
00305 repeat:
00306 disable();
00307 // If the task's console is not the current console auto-sleep //
00308 if ( ct->console != get_curr_console() )
00309 {
00310 add_queue( &keyb_queue, ct );
00311 sleep_task( ct );
00312 enable();
00313 idle();
00314 goto repeat;
00315 }
00316 // If the keyboard buffer is empty enable interrupts and wait //
00317 if ( cons->keyb_buf_count==0 )
00318 {
00319 enable();
00320 idle();
00321 goto repeat;
00322 }
00323
00324 // Update keyboard buffer in mutual exclusion //
00325 (cons->keyb_buf_count)--;
00326 if ( ++(cons->keyb_buf_read) >= KEYB_BUF_DIM )
00327 cons->keyb_buf_read = 0;
00328 key = cons->keyb_buffer[cons->keyb_buf_read];
00329
00330 SET_IF(IF);
00331
00332 return( key );
00333 }
|
|
|
Get the hitten key keyboard code.
Definition at line 123 of file keyboard.c.
00124 {
00125 static int code, val;
00126 dword IF = GET_IF();
00127
00128 disable();
00129
00130 code = inportb(KEYB_PORT); // Get scan code
00131 val = inportb(KEYB_ACK); // Get keyboard acknowledge
00132 outportb(KEYB_ACK, val | 0x80); // Disable bit 7
00133 outportb(KEYB_ACK, val); // Send that back
00134
00135 SET_IF(IF);
00136
00137 return code;
00138 }
|
|
|
Update keyboard leds.
Definition at line 101 of file keyboard.c.
00102 {
00103 int leds;
00104 console_t *curr_cons = get_console_addr( get_curr_console() );
00105 dword IF = GET_IF();
00106
00107 leds = (curr_cons->scroll_lock) |
00108 (curr_cons->num_lock << 1) |
00109 (curr_cons->caps_lock << 2);
00110
00111 disable();
00112
00113 keyb_wait();
00114 outportb(KEYB_PORT, KEYB_LED_CODE);
00115 keyb_wait();
00116 outportb(KEYB_PORT, leds);
00117
00118 SET_IF(IF);
00119 }
|
1.2.18