* Added the opportunity to add temporary debug interrupt handlers for
arch dependent code (they will be removed as soon as someone else asks for these interrupt lines). * Added an interrupt driven keyboard handler to the kernel that uses this technique. As a result, you can now press F12 to enter the kernel debugger before the input_server has been started, and Control-Alt-Delete should reboot the system (actually I did not test the latter yet). git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@17806 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
parent
099e443467
commit
d51ce54011
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2005, Axel Dörfler, axeld@pinc-software.de
|
||||
* Copyright 2002-2006, Axel Dörfler, axeld@pinc-software.de
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Copyright 2001-2002, Travis Geiselbrecht. All rights reserved.
|
||||
@ -24,6 +24,9 @@ void arch_debug_serial_putchar(char c);
|
||||
void arch_debug_serial_puts(const char *s);
|
||||
void arch_debug_serial_early_boot_message(const char *string);
|
||||
|
||||
void arch_debug_remove_interrupt_handler(uint32 line);
|
||||
void arch_debug_install_interrupt_handlers(void);
|
||||
|
||||
status_t arch_debug_console_init(struct kernel_args *args);
|
||||
status_t arch_debug_console_init_settings(struct kernel_args *args);
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2003-2005, Axel Dörfler, axeld@pinc-software.de.
|
||||
* Copyright 2003-2006, Axel Dörfler, axeld@pinc-software.de.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Copyright 2001, Travis Geiselbrecht. All rights reserved.
|
||||
@ -16,6 +16,18 @@
|
||||
#include <string.h>
|
||||
|
||||
|
||||
void
|
||||
arch_debug_remove_interrupt_handler(uint32 line)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
arch_debug_install_interrupt_handlers(void)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
char
|
||||
arch_debug_blue_screen_getchar(void)
|
||||
{
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2005, Axel Dörfler, axeld@pinc-software.de
|
||||
* Copyright 2002-2006, Axel Dörfler, axeld@pinc-software.de
|
||||
* Copyright 2001, Rob Judd <judd@ob-wan.com>
|
||||
* Copyright 2002, Marcus Overhagen <marcus@overhagen.de>
|
||||
* Distributed under the terms of the Haiku License.
|
||||
@ -14,9 +14,9 @@
|
||||
#include <KernelExport.h>
|
||||
#include <driver_settings.h>
|
||||
#include <int.h>
|
||||
|
||||
#include <arch/cpu.h>
|
||||
#include <arch/debug_console.h>
|
||||
|
||||
#include <boot/stage2.h>
|
||||
|
||||
#include <string.h>
|
||||
@ -45,11 +45,54 @@ enum serial_register_offsets {
|
||||
SERIAL_MODEM_STATUS = 6,
|
||||
};
|
||||
|
||||
enum keycodes {
|
||||
LEFT_SHIFT = 42,
|
||||
RIGHT_SHIFT = 54,
|
||||
|
||||
LEFT_CONTROL = 29,
|
||||
RIGHT_CONTROL = 157,
|
||||
|
||||
LEFT_ALT = 56,
|
||||
RIGHT_ALT = 184,
|
||||
|
||||
CURSOR_LEFT = 75,
|
||||
CURSOR_RIGHT = 77,
|
||||
CURSOR_UP = 72,
|
||||
CURSOR_DOWN = 80,
|
||||
|
||||
BREAK = 198,
|
||||
DELETE = 201,
|
||||
F12 = 88,
|
||||
};
|
||||
|
||||
static const char kUnshiftedKeymap[128] = {
|
||||
0, 27, '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=', 8, '\t',
|
||||
'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n', 0, 'a', 's',
|
||||
'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'', '`', 0, '\\', 'z', 'x', 'c', 'v',
|
||||
'b', 'n', 'm', ',', '.', '/', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
'\\', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
|
||||
};
|
||||
|
||||
static const char kShiftedKeymap[128] = {
|
||||
0, 27, '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+', 8, '\t',
|
||||
'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P', '{', '}', '\n', 0, 'A', 'S',
|
||||
'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '"', '~', 0, '|', 'Z', 'X', 'C', 'V',
|
||||
'B', 'N', 'M', '<', '>', '?', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
|
||||
};
|
||||
|
||||
static const uint32 kSerialBaudRate = 115200;
|
||||
|
||||
static uint16 sSerialBasePort = 0x3f8;
|
||||
// COM1 is the default debug output port
|
||||
|
||||
static bool sKeyboardHandlerInstalled = false;
|
||||
#if BOCHS_DEBUG_HACK
|
||||
static bool sBochsOutput = false;
|
||||
#endif
|
||||
@ -73,43 +116,90 @@ put_char(const char c)
|
||||
}
|
||||
|
||||
|
||||
/** Minimal keyboard handler to be able to get into the debugger and
|
||||
* reboot the machine before the input_server is up and running.
|
||||
* It is added as soon as interrupts become available, and removed
|
||||
* again if anything else requests the interrupt 1.
|
||||
*/
|
||||
|
||||
static int32
|
||||
debug_keyboard_interrupt(void *data)
|
||||
{
|
||||
static bool controlPressed;
|
||||
static bool altPressed;
|
||||
uint8 key;
|
||||
|
||||
key = in8(PS2_PORT_DATA);
|
||||
//dprintf("debug_keyboard_interrupt: key = 0x%x\n", key);
|
||||
|
||||
if (key & 0x80) {
|
||||
if (key == LEFT_CONTROL)
|
||||
controlPressed = false;
|
||||
if (key == LEFT_ALT)
|
||||
altPressed = false;
|
||||
|
||||
return B_HANDLED_INTERRUPT;
|
||||
}
|
||||
|
||||
switch (key) {
|
||||
case LEFT_CONTROL:
|
||||
controlPressed = true;
|
||||
break;
|
||||
|
||||
case LEFT_ALT:
|
||||
altPressed = true;
|
||||
break;
|
||||
|
||||
case DELETE:
|
||||
if (controlPressed && altPressed)
|
||||
arch_cpu_shutdown(true);
|
||||
break;
|
||||
|
||||
/* the following code has two possibilities because of issues
|
||||
* with BeBochs & BeOS (all special keys don't map to anything
|
||||
* useful, and SYS_REQ does a screen dump in BeOS).
|
||||
* ToDo: remove these key functions some day...
|
||||
*/
|
||||
case F12:
|
||||
case BREAK:
|
||||
panic("Keyboard Requested Halt\n");
|
||||
break;
|
||||
}
|
||||
|
||||
return B_HANDLED_INTERRUPT;
|
||||
}
|
||||
|
||||
|
||||
// #pragma mark -
|
||||
|
||||
|
||||
void
|
||||
arch_debug_remove_interrupt_handler(uint32 line)
|
||||
{
|
||||
if (line != INT_PS2_KEYBOARD || !sKeyboardHandlerInstalled)
|
||||
return;
|
||||
|
||||
remove_io_interrupt_handler(INT_PS2_KEYBOARD, &debug_keyboard_interrupt,
|
||||
NULL);
|
||||
sKeyboardHandlerInstalled = false;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
arch_debug_install_interrupt_handlers(void)
|
||||
{
|
||||
install_io_interrupt_handler(INT_PS2_KEYBOARD, &debug_keyboard_interrupt,
|
||||
NULL, 0);
|
||||
sKeyboardHandlerInstalled = true;
|
||||
}
|
||||
|
||||
|
||||
char
|
||||
arch_debug_blue_screen_getchar(void)
|
||||
{
|
||||
/* polling the keyboard, similar to code in keyboard
|
||||
* driver, but without using an interrupt
|
||||
*/
|
||||
static const char unshifted_keymap[128] = {
|
||||
0, 27, '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=', 8, '\t',
|
||||
'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n', 0, 'a', 's',
|
||||
'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'', '`', 0, '\\', 'z', 'x', 'c', 'v',
|
||||
'b', 'n', 'm', ',', '.', '/', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
'\\', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
|
||||
};
|
||||
static const char shifted_keymap[128] = {
|
||||
0, 27, '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+', 8, '\t',
|
||||
'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P', '{', '}', '\n', 0, 'A', 'S',
|
||||
'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '"', '~', 0, '|', 'Z', 'X', 'C', 'V',
|
||||
'B', 'N', 'M', '<', '>', '?', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
|
||||
};
|
||||
enum keycodes {
|
||||
LSHIFT = 42,
|
||||
RSHIFT = 54,
|
||||
CURSOR_LEFT = 75,
|
||||
CURSOR_RIGHT = 77,
|
||||
CURSOR_UP = 72,
|
||||
CURSOR_DOWN = 80,
|
||||
};
|
||||
static bool shift = false;
|
||||
static uint8 special = 0;
|
||||
uint8 key, ascii = 0;
|
||||
@ -143,13 +233,13 @@ arch_debug_blue_screen_getchar(void)
|
||||
|
||||
if (key & 0x80) {
|
||||
// key up
|
||||
if (key == (0x80 | LSHIFT) || key == (0x80 | RSHIFT))
|
||||
if (key == (0x80 | LEFT_SHIFT) || key == (0x80 | RIGHT_SHIFT))
|
||||
shift = false;
|
||||
} else {
|
||||
// key down
|
||||
switch (key) {
|
||||
case LSHIFT:
|
||||
case RSHIFT:
|
||||
case LEFT_SHIFT:
|
||||
case RIGHT_SHIFT:
|
||||
shift = true;
|
||||
break;
|
||||
|
||||
@ -168,7 +258,7 @@ arch_debug_blue_screen_getchar(void)
|
||||
return '\x1b';
|
||||
|
||||
default:
|
||||
return shift ? shifted_keymap[key] : unshifted_keymap[key];
|
||||
return shift ? kShiftedKeymap[key] : kUnshiftedKeymap[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -10,8 +10,10 @@
|
||||
#include <int.h>
|
||||
#include <smp.h>
|
||||
#include <util/kqueue.h>
|
||||
#include <boot/kernel_args.h>
|
||||
|
||||
#include <arch/debug_console.h>
|
||||
#include <arch/int.h>
|
||||
#include <boot/kernel_args.h>
|
||||
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
@ -129,6 +131,8 @@ int_init_post_vm(kernel_args *args)
|
||||
status_t
|
||||
int_init_post_device_manager(kernel_args *args)
|
||||
{
|
||||
arch_debug_install_interrupt_handlers();
|
||||
|
||||
return arch_int_init_post_device_manager(args);
|
||||
}
|
||||
|
||||
@ -150,6 +154,10 @@ install_io_interrupt_handler(long vector, interrupt_handler handler, void *data,
|
||||
if (io == NULL)
|
||||
return B_NO_MEMORY;
|
||||
|
||||
arch_debug_remove_interrupt_handler(vector);
|
||||
// There might be a temporary debug interrupt installed on this
|
||||
// vector that should be removed now.
|
||||
|
||||
io->func = handler;
|
||||
io->data = data;
|
||||
io->use_enable_counter = (flags & B_NO_ENABLE_COUNTER) == 0;
|
||||
|
Loading…
Reference in New Issue
Block a user