📄 keyboard.c
字号:
13267 capslock = 1 - capslock;
13268 set_leds();
13269 }
13270 caps_off = 1 - make;
13271 ch = -1;
13272 break;
13273 case NLOCK:
13274 if (make && num_off) {
13275 numlock = 1 - numlock;
13276 set_leds();
13277 }
13278 num_off = 1 - make;
13279 ch = -1;
13280 break;
13281 case SLOCK:
13282 if (make & slock_off) {
13283 slock = 1 - slock;
13284 set_leds();
13285 }
13286 slock_off = 1 - make;
13287 ch = -1;
13288 break;
13289 case EXTKEY:
13290 esc = 1;
13291 return(-1);
13292 default:
13293 if (!make) ch = -1;
13294 }
13295 esc = 0;
13296 return(ch);
13297 }
13300 /*===========================================================================*
13301 * set_leds *
13302 *===========================================================================*/
13303 PRIVATE void set_leds()
13304 {
13305 /* Set the LEDs on the caps lock and num lock keys */
13306
13307 unsigned leds;
13308
13309 if (!pc_at) return; /* PC/XT doesn't have LEDs */
13310
13311 /* encode LED bits */
13312 leds = (slock << 0) | (numlock << 1) | (capslock << 2);
13313
13314 kb_wait(); /* wait for buffer empty */
13315 out_byte(KEYBD, LED_CODE); /* prepare keyboard to accept LED values */
13316 kb_ack(); /* wait for ack response */
13317
13318 kb_wait(); /* wait for buffer empty */
13319 out_byte(KEYBD, leds); /* give keyboard LED values */
13320 kb_ack(); /* wait for ack response */
13321 }
13324 /*==========================================================================*
13325 * kb_wait *
13326 *==========================================================================*/
13327 PRIVATE int kb_wait()
13328 {
13329 /* Wait until the controller is ready; return zero if this times out. */
13330
13331 int retries;
13332
13333 retries = MAX_KB_BUSY_RETRIES + 1;
13334 while (--retries != 0 && in_byte(KB_STATUS) & KB_BUSY)
13335 ; /* wait until not busy */
13336 return(retries); /* nonzero if ready */
13337 }
13340 /*==========================================================================*
13341 * kb_ack *
13342 *==========================================================================*/
13343 PRIVATE int kb_ack()
13344 {
13345 /* Wait until kbd acknowledges last command; return zero if this times out. */
13346
13347 int retries;
13348
13349 retries = MAX_KB_ACK_RETRIES + 1;
13350 while (--retries != 0 && in_byte(KEYBD) != KB_ACK)
13351 ; /* wait for ack */
13352 return(retries); /* nonzero if ack received */
13353 }
13356 /*===========================================================================*
13357 * kb_init *
13358 *===========================================================================*/
13359 PUBLIC void kb_init(tp)
13360 tty_t *tp;
13361 {
13362 /* Initialize the keyboard driver. */
13363
13364 register struct kb_s *kb;
13365
13366 /* Input function. */
13367 tp->tty_devread = kb_read;
13368
13369 kb = kb_addr();
13370
13371 /* Set up input queue. */
13372 kb->ihead = kb->itail = kb->ibuf;
13373
13374 /* Set initial values. */
13375 caps_off = 1;
13376 num_off = 1;
13377 slock_off = 1;
13378 esc = 0;
13379
13380 set_leds(); /* turn off numlock led */
13381
13382 scan_keyboard(); /* stop lockup from leftover keystroke */
13383
13384 put_irq_handler(KEYBOARD_IRQ, kbd_hw_int); /* set the interrupt handler */
13385 enable_irq(KEYBOARD_IRQ); /* safe now everything initialised! */
13386 }
13389 /*===========================================================================*
13390 * kbd_loadmap *
13391 *===========================================================================*/
13392 PUBLIC int kbd_loadmap(user_phys)
13393 phys_bytes user_phys;
13394 {
13395 /* Load a new keymap. */
13396
13397 phys_copy(user_phys, vir2phys(keymap), (phys_bytes) sizeof(keymap));
13398 return(OK);
13399 }
13402 /*===========================================================================*
13403 * func_key *
13404 *===========================================================================*/
13405 PRIVATE int func_key(scode)
13406 int scode; /* scan code for a function key */
13407 {
13408 /* This procedure traps function keys for debugging and control purposes. */
13409
13410 unsigned code;
13411
13412 code = map_key0(scode); /* first ignore modifiers */
13413 if (code < F1 || code > F12) return(FALSE); /* not our job */
13414
13415 switch (map_key(scode)) { /* include modifiers */
13416
13417 case F1: p_dmp(); break; /* print process table */
13418 case F2: map_dmp(); break; /* print memory map */
13419 case F3: toggle_scroll(); break; /* hardware vs. software scrolling */
13420 case CF7: sigchar(&tty_table[CONSOLE], SIGQUIT); break;
13421 case CF8: sigchar(&tty_table[CONSOLE], SIGINT); break;
13422 case CF9: sigchar(&tty_table[CONSOLE], SIGKILL); break;
13423 default: return(FALSE);
13424 }
13425 return(TRUE);
13426 }
13429 /*==========================================================================*
13430 * scan_keyboard *
13431 *==========================================================================*/
13432 PRIVATE int scan_keyboard()
13433 {
13434 /* Fetch the character from the keyboard hardware and acknowledge it. */
13435
13436 int code;
13437 int val;
13438
13439 code = in_byte(KEYBD); /* get the scan code for the key struck */
13440 val = in_byte(PORT_B); /* strobe the keyboard to ack the char */
13441 out_byte(PORT_B, val | KBIT); /* strobe the bit high */
13442 out_byte(PORT_B, val); /* now strobe it low */
13443 return code;
13444 }
13447 /*==========================================================================*
13448 * wreboot *
13449 *==========================================================================*/
13450 PUBLIC void wreboot(how)
13451 int how; /* 0 = halt, 1 = reboot, 2 = panic!, ... */
13452 {
13453 /* Wait for keystrokes for printing debugging info and reboot. */
13454
13455 int quiet, code;
13456 static u16_t magic = MEMCHECK_MAG;
13457 struct tasktab *ttp;
13458
13459 /* Mask all interrupts. */
13460 out_byte(INT_CTLMASK, ~0);
13461
13462 /* Tell several tasks to stop. */
13463 cons_stop();
13464 floppy_stop();
13465 clock_stop();
13466
13467 if (how == RBT_HALT) {
13468 printf("System Halted\n");
13469 if (!mon_return) how = RBT_PANIC;
13470 }
13471
13472 if (how == RBT_PANIC) {
13473 /* A panic! */
13474 printf("Hit ESC to reboot, F-keys for debug dumps\n");
13475
13476 (void) scan_keyboard(); /* ack any old input */
13477 quiet = scan_keyboard();/* quiescent value (0 on PC, last code on AT)*/
13478 for (;;) {
13479 milli_delay(100); /* pause for a decisecond */
13480 code = scan_keyboard();
13481 if (code != quiet) {
13482 /* A key has been pressed. */
13483 if (code == ESC_SCAN) break; /* reboot if ESC typed */
13484 (void) func_key(code); /* process function key */
13485 quiet = scan_keyboard();
13486 }
13487 }
13488 how = RBT_REBOOT;
13489 }
13490
13491 if (how == RBT_REBOOT) printf("Rebooting\n");
13492
13493 if (mon_return && how != RBT_RESET) {
13494 /* Reinitialize the interrupt controllers to the BIOS defaults. */
13495 intr_init(0);
13496 out_byte(INT_CTLMASK, 0);
13497 out_byte(INT2_CTLMASK, 0);
13498
13499 /* Return to the boot monitor. */
13500 if (how == RBT_HALT) {
13501 reboot_code = vir2phys("");
13502 } else
13503 if (how == RBT_REBOOT) {
13504 reboot_code = vir2phys("delay;boot");
13505 }
13506 level0(monitor);
13507 }
13508
13509 /* Stop BIOS memory test. */
13510 phys_copy(vir2phys(&magic), (phys_bytes) MEMCHECK_ADR,
13511 (phys_bytes) sizeof(magic));
13512
13513 if (protected_mode) {
13514 /* Use the AT keyboard controller to reset the processor.
13515 * The A20 line is kept enabled in case this code is ever
13516 * run from extended memory, and because some machines
13517 * appear to drive the fake A20 high instead of low just
13518 * after reset, leading to an illegal opode trap. This bug
13519 * is more of a problem if the fake A20 is in use, as it
13520 * would be if the keyboard reset were used for real mode.
13521 */
13522 kb_wait();
13523 out_byte(KB_COMMAND,
13524 KB_PULSE_OUTPUT | (0x0F & ~(KB_GATE_A20 | KB_RESET)));
13525 milli_delay(10);
13526
13527 /* If the nice method fails then do a reset. In protected
13528 * mode this means a processor shutdown.
13529 */
13530 printf("Hard reset...\n");
13531 milli_delay(250);
13532 }
13533 /* In real mode, jumping to the reset address is good enough. */
13534 level0(reset);
13535 }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -