Index: Makefile
===================================================================
--- Makefile	(revision 108602edcc3c9087905062b8132e7aa21999ee3a)
+++ Makefile	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -45,5 +45,6 @@
 endif
 ifeq ($(ARCH), ia32)
-	DIRS += pci
+	DIRS += pci \
+		kbd
 endif
 
Index: init/Makefile
===================================================================
--- init/Makefile	(revision 108602edcc3c9087905062b8132e7aa21999ee3a)
+++ init/Makefile	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -35,5 +35,5 @@
 include $(LIBC_PREFIX)/Makefile.toolchain
 
-CFLAGS += -I../libipc/include
+CFLAGS += -I../libipc/include -I../kbd/include
 
 LIBS = $(LIBIPC_PREFIX)/libipc.a $(LIBC_PREFIX)/libc.a
Index: init/init.c
===================================================================
--- init/init.c	(revision 108602edcc3c9087905062b8132e7aa21999ee3a)
+++ init/init.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -40,4 +40,5 @@
 #include <ddi.h>
 #include <string.h>
+#include <kbd.h>
 
 int a;
@@ -293,4 +294,26 @@
 }
 
+static void test_kbd()
+{
+	int res;
+	ipcarg_t result;
+	int phoneid;
+
+	printf("Test: Starting connect...\n");
+	while ((phoneid = ipc_connect_me_to(PHONE_NS, 30, 60)) < 0) {
+	};
+	
+	printf("Test: Connected: %d\n", res);
+	printf("Test: pinging.\n");
+	while (1) {
+		res = ipc_call_sync(phoneid, KBD_GETCHAR, 0xbeef,&result);
+//		printf("Test: Retval: %d - received: %c\n", res, result);
+		printf("%c", result);
+	}
+	
+	printf("Test: Hangin up\n");
+	ipc_hangup(phoneid);
+}
+
 static int test_as_send()
 {
@@ -331,5 +354,7 @@
 //	test_hangup();
 //	test_slam();
-	test_as_send();
+//	test_as_send();
+	test_kbd();
+
 /*	
 	printf("Userspace task, taskid=%llX\n", task_get_id());
Index: kbd/Makefile
===================================================================
--- kbd/Makefile	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/Makefile	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,83 @@
+#
+# Copyright (C) 2005 Martin Decky
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+#
+# - Redistributions of source code must retain the above copyright
+#   notice, this list of conditions and the following disclaimer.
+# - Redistributions in binary form must reproduce the above copyright
+#   notice, this list of conditions and the following disclaimer in the
+#   documentation and/or other materials provided with the distribution.
+# - The name of the author may not be used to endorse or promote products
+#   derived from this software without specific prior written permission.
+#
+# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+# OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+# IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+#
+
+## Setup toolchain
+#
+
+LIBC_PREFIX = ../libc
+LIBIPC_PREFIX = ../libipc
+SOFTINT_PREFIX = ../softint
+include $(LIBC_PREFIX)/Makefile.toolchain 
+
+CFLAGS += -Iinclude -I../libipc/include -I../libadt/include
+
+LIBS = $(LIBIPC_PREFIX)/libipc.a $(LIBC_PREFIX)/libc.a
+
+## Sources
+#
+
+OUTPUT = kbd
+GENERIC_SOURCES = \
+	generic/kbd.c \
+	generic/key_buffer.c
+
+ARCH_SOURCES = \
+	arch/$(ARCH)/src/kbd.c
+
+GENERIC_OBJECTS := $(addsuffix .o,$(basename $(GENERIC_SOURCES)))
+ARCH_OBJECTS := $(addsuffix .o,$(basename $(ARCH_SOURCES)))
+
+.PHONY: all clean depend disasm links
+
+all: links $(OUTPUT) disasm
+
+-include Makefile.depend
+
+links:
+	ln -sfn ../arch/$(ARCH)/include include/arch
+
+clean:
+	-rm -f $(OUTPUT) $(OUTPUT).map $(OUTPUT).disasm Makefile.depend include/arch
+
+depend:
+	$(CC) $(DEFS) $(CFLAGS) -M $(SOURCES) > Makefile.depend
+
+$(OUTPUT): $(ARCH_OBJECTS) $(GENERIC_OBJECTS) $(LIBS)
+	$(LD) -T $(LIBC_PREFIX)/arch/$(ARCH)/_link.ld  $(GENERIC_OBJECTS) $(ARCH_OBJECTS) $(LIBS) $(LFLAGS) -o $@ -Map $(OUTPUT).map
+
+disasm:
+	$(OBJDUMP) -d $(OUTPUT) >$(OUTPUT).disasm
+
+%.o: %.S
+	$(CC) $(DEFS) $(AFLAGS) $(CFLAGS) -D__ASM__ -c $< -o $@
+
+%.o: %.s
+	$(AS) $(AFLAGS) $< -o $@
+
+%.o: %.c
+	$(CC) $(DEFS) $(CFLAGS) -c $< -o $@
Index: kbd/arch/ia32/include/kbd.h
===================================================================
--- kbd/arch/ia32/include/kbd.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/arch/ia32/include/kbd.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __ia32_KBD_H__
+#define __ia32_KBD_H__
+
+int kbd_arch_init(void);
+int kbd_arch_process(int scan_code);
+
+#endif
Index: kbd/arch/ia32/src/kbd.c
===================================================================
--- kbd/arch/ia32/src/kbd.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/arch/ia32/src/kbd.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,349 @@
+/*
+ * Copyright (C) 2001-2004 Jakub Jermar
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <arch/kbd.h>
+#include <key_buffer.h>
+#include <ipc.h>
+
+#define SPECIAL		'?'
+#define KEY_RELEASE	0x80
+
+/**
+ * These codes read from i8042 data register are silently ignored.
+ */
+#define IGNORE_CODE	0x7f
+
+#define PRESSED_SHIFT		(1<<0)
+#define PRESSED_CAPSLOCK	(1<<1)
+#define LOCKED_CAPSLOCK		(1<<0)
+
+/** Scancodes. */
+#define SC_ESC		0x01
+#define SC_BACKSPACE	0x0e
+#define SC_LSHIFT	0x2a
+#define SC_RSHIFT	0x36
+#define SC_CAPSLOCK	0x3a
+#define SC_SPEC_ESCAPE  0xe0
+#define SC_LEFTARR      0x4b
+#define SC_RIGHTARR     0x4d
+#define SC_UPARR        0x48
+#define SC_DOWNARR      0x50
+#define SC_DELETE       0x53
+#define SC_HOME         0x47
+#define SC_END          0x4f
+
+static volatile int keyflags;		/**< Tracking of multiple keypresses. */
+static volatile int lockflags;		/**< Tracking of multiple keys lockings. */
+
+/** Primary meaning of scancodes. */
+static char sc_primary_map[] = {
+	SPECIAL, /* 0x00 */
+	SPECIAL, /* 0x01 - Esc */
+	'1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=',
+	'\b', /* 0x0e - Backspace */
+	'\t', 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n',
+	SPECIAL, /* 0x1d - LCtrl */
+	'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'',
+	'`',
+	SPECIAL, /* 0x2a - LShift */ 
+	'\\',
+	'z', 'x', 'c', 'v', 'b', 'n', 'm', ',', '.', '/',
+	SPECIAL, /* 0x36 - RShift */
+	'*',
+	SPECIAL, /* 0x38 - LAlt */
+	' ',
+	SPECIAL, /* 0x3a - CapsLock */
+	SPECIAL, /* 0x3b - F1 */
+	SPECIAL, /* 0x3c - F2 */
+	SPECIAL, /* 0x3d - F3 */
+	SPECIAL, /* 0x3e - F4 */
+	SPECIAL, /* 0x3f - F5 */
+	SPECIAL, /* 0x40 - F6 */
+	SPECIAL, /* 0x41 - F7 */
+	SPECIAL, /* 0x42 - F8 */
+	SPECIAL, /* 0x43 - F9 */
+	SPECIAL, /* 0x44 - F10 */
+	SPECIAL, /* 0x45 - NumLock */
+	SPECIAL, /* 0x46 - ScrollLock */
+	'7', '8', '9', '-',
+	'4', '5', '6', '+',
+	'1', '2', '3',
+	'0', '.',
+	SPECIAL, /* 0x54 - Alt-SysRq */
+	SPECIAL, /* 0x55 - F11/F12/PF1/FN */
+	SPECIAL, /* 0x56 - unlabelled key next to LAlt */
+	SPECIAL, /* 0x57 - F11 */
+	SPECIAL, /* 0x58 - F12 */
+	SPECIAL, /* 0x59 */
+	SPECIAL, /* 0x5a */
+	SPECIAL, /* 0x5b */
+	SPECIAL, /* 0x5c */
+	SPECIAL, /* 0x5d */
+	SPECIAL, /* 0x5e */
+	SPECIAL, /* 0x5f */
+	SPECIAL, /* 0x60 */
+	SPECIAL, /* 0x61 */
+	SPECIAL, /* 0x62 */
+	SPECIAL, /* 0x63 */
+	SPECIAL, /* 0x64 */
+	SPECIAL, /* 0x65 */
+	SPECIAL, /* 0x66 */
+	SPECIAL, /* 0x67 */
+	SPECIAL, /* 0x68 */
+	SPECIAL, /* 0x69 */
+	SPECIAL, /* 0x6a */
+	SPECIAL, /* 0x6b */
+	SPECIAL, /* 0x6c */
+	SPECIAL, /* 0x6d */
+	SPECIAL, /* 0x6e */
+	SPECIAL, /* 0x6f */
+	SPECIAL, /* 0x70 */
+	SPECIAL, /* 0x71 */
+	SPECIAL, /* 0x72 */
+	SPECIAL, /* 0x73 */
+	SPECIAL, /* 0x74 */
+	SPECIAL, /* 0x75 */
+	SPECIAL, /* 0x76 */
+	SPECIAL, /* 0x77 */
+	SPECIAL, /* 0x78 */
+	SPECIAL, /* 0x79 */
+	SPECIAL, /* 0x7a */
+	SPECIAL, /* 0x7b */
+	SPECIAL, /* 0x7c */
+	SPECIAL, /* 0x7d */
+	SPECIAL, /* 0x7e */
+	SPECIAL, /* 0x7f */
+};
+
+/** Secondary meaning of scancodes. */
+static char sc_secondary_map[] = {
+	SPECIAL, /* 0x00 */
+	SPECIAL, /* 0x01 - Esc */
+	'!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+',
+	SPECIAL, /* 0x0e - Backspace */
+	'\t', 'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P', '{', '}', '\n',
+	SPECIAL, /* 0x1d - LCtrl */
+	'A', 'S', 'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '"',
+	'~',
+	SPECIAL, /* 0x2a - LShift */ 
+	'|',
+	'Z', 'X', 'C', 'V', 'B', 'N', 'M', '<', '>', '?',
+	SPECIAL, /* 0x36 - RShift */
+	'*',
+	SPECIAL, /* 0x38 - LAlt */
+	' ',
+	SPECIAL, /* 0x3a - CapsLock */
+	SPECIAL, /* 0x3b - F1 */
+	SPECIAL, /* 0x3c - F2 */
+	SPECIAL, /* 0x3d - F3 */
+	SPECIAL, /* 0x3e - F4 */
+	SPECIAL, /* 0x3f - F5 */
+	SPECIAL, /* 0x40 - F6 */
+	SPECIAL, /* 0x41 - F7 */
+	SPECIAL, /* 0x42 - F8 */
+	SPECIAL, /* 0x43 - F9 */
+	SPECIAL, /* 0x44 - F10 */
+	SPECIAL, /* 0x45 - NumLock */
+	SPECIAL, /* 0x46 - ScrollLock */
+	'7', '8', '9', '-',
+	'4', '5', '6', '+',
+	'1', '2', '3',
+	'0', '.',
+	SPECIAL, /* 0x54 - Alt-SysRq */
+	SPECIAL, /* 0x55 - F11/F12/PF1/FN */
+	SPECIAL, /* 0x56 - unlabelled key next to LAlt */
+	SPECIAL, /* 0x57 - F11 */
+	SPECIAL, /* 0x58 - F12 */
+	SPECIAL, /* 0x59 */
+	SPECIAL, /* 0x5a */
+	SPECIAL, /* 0x5b */
+	SPECIAL, /* 0x5c */
+	SPECIAL, /* 0x5d */
+	SPECIAL, /* 0x5e */
+	SPECIAL, /* 0x5f */
+	SPECIAL, /* 0x60 */
+	SPECIAL, /* 0x61 */
+	SPECIAL, /* 0x62 */
+	SPECIAL, /* 0x63 */
+	SPECIAL, /* 0x64 */
+	SPECIAL, /* 0x65 */
+	SPECIAL, /* 0x66 */
+	SPECIAL, /* 0x67 */
+	SPECIAL, /* 0x68 */
+	SPECIAL, /* 0x69 */
+	SPECIAL, /* 0x6a */
+	SPECIAL, /* 0x6b */
+	SPECIAL, /* 0x6c */
+	SPECIAL, /* 0x6d */
+	SPECIAL, /* 0x6e */
+	SPECIAL, /* 0x6f */
+	SPECIAL, /* 0x70 */
+	SPECIAL, /* 0x71 */
+	SPECIAL, /* 0x72 */
+	SPECIAL, /* 0x73 */
+	SPECIAL, /* 0x74 */
+	SPECIAL, /* 0x75 */
+	SPECIAL, /* 0x76 */
+	SPECIAL, /* 0x77 */
+	SPECIAL, /* 0x78 */
+	SPECIAL, /* 0x79 */
+	SPECIAL, /* 0x7a */
+	SPECIAL, /* 0x7b */
+	SPECIAL, /* 0x7c */
+	SPECIAL, /* 0x7d */
+	SPECIAL, /* 0x7e */
+	SPECIAL, /* 0x7f */	
+};
+
+irq_cmd_t i8042_cmds[1] = {
+	{ CMD_PORT_READ_1, (void *)0x60, 0 }
+};
+
+irq_code_t i8042_kbd = {
+	1,
+	i8042_cmds
+};
+
+static int key_released(unsigned char key)
+{
+	switch (key) {
+		case SC_LSHIFT:
+		case SC_RSHIFT:
+			keyflags &= ~PRESSED_SHIFT;
+			break;
+		case SC_CAPSLOCK:
+			keyflags &= ~PRESSED_CAPSLOCK;
+			if (lockflags & LOCKED_CAPSLOCK)
+				lockflags &= ~LOCKED_CAPSLOCK;
+				else
+				lockflags |= LOCKED_CAPSLOCK;
+			break;
+		default:
+			break;
+	}
+}
+
+static int key_pressed(unsigned char key)
+{
+	char *map = sc_primary_map;
+	char ascii = sc_primary_map[key];
+	char shift, capslock;
+	char letter = 0;
+
+	switch (key) {
+		case SC_LSHIFT:
+		case SC_RSHIFT:
+		    	keyflags |= PRESSED_SHIFT;
+			break;
+		case SC_CAPSLOCK:
+			keyflags |= PRESSED_CAPSLOCK;
+			break;
+		case SC_SPEC_ESCAPE:
+			break;
+		case SC_LEFTARR:
+			if (key_buffer_available() >= 3) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x5b);	
+				key_buffer_push(0x44);	
+			}
+			break;
+		case SC_RIGHTARR:
+			if (key_buffer_available() >= 3) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x5b);	
+				key_buffer_push(0x43);	
+			}
+			break;
+		case SC_UPARR:
+			if (key_buffer_available() >= 3) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x5b);	
+				key_buffer_push(0x41);	
+			}
+			break;
+		case SC_DOWNARR:
+			if (key_buffer_available() >= 3) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x5b);	
+				key_buffer_push(0x42);	
+			}
+			break;
+		case SC_HOME:
+			if (key_buffer_available() >= 3) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x4f);	
+				key_buffer_push(0x48);	
+			}
+			break;
+		case SC_END:
+			if (key_buffer_available() >= 3) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x4f);	
+				key_buffer_push(0x46);	
+			}
+			break;
+		case SC_DELETE:
+			if (key_buffer_available() >= 4) {
+				key_buffer_push(0x1b);	
+				key_buffer_push(0x5b);	
+				key_buffer_push(0x33);	
+				key_buffer_push(0x7e);	
+			}
+			break;
+		default:
+		    	letter = ((ascii >= 'a') && (ascii <= 'z'));
+			capslock = (keyflags & PRESSED_CAPSLOCK) || (lockflags & LOCKED_CAPSLOCK);
+			shift = keyflags & PRESSED_SHIFT;
+			if (letter && capslock)
+				shift = !shift;
+			if (shift)
+				map = sc_secondary_map;
+			key_buffer_push(map[key]);	
+			break;
+	}
+}
+
+/** Register uspace irq handler
+ * @return 
+ */
+int kbd_arch_init(void)
+{
+	return !(ipc_register_irq(1, &i8042_kbd));
+}
+
+int kbd_arch_process(int scan_code)
+{
+	if (scan_code != IGNORE_CODE) {
+		if (scan_code & KEY_RELEASE)
+			key_released(scan_code ^ KEY_RELEASE);
+		else
+			key_pressed(scan_code);
+	}
+	return 	1;
+}
Index: kbd/arch/mips32/include/kbd.h
===================================================================
--- kbd/arch/mips32/include/kbd.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/arch/mips32/include/kbd.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __mips32_KBD_H__
+#define __mips32_KBD_H__
+
+void kbd_arch_init(void);
+
+#endif
+
Index: kbd/arch/mips32/src/kbd.c
===================================================================
--- kbd/arch/mips32/src/kbd.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/arch/mips32/src/kbd.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <arch/kbd.h>
+#include <ipc.h>
+
+irq_cmd_t msim_cmds[1] = {
+	{ CMD_MEM_READ_1, (void *)0xB0000000, 0 }
+};
+
+irq_code_t msim_kbd = {
+	1,
+	msim_cmds
+};
+
+void kbd_arch_init(void)
+{
+	ipc_register_irq(2, &msim_kbd);
+}
+
+
Index: kbd/generic/kbd.c
===================================================================
--- kbd/generic/kbd.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/generic/kbd.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,144 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <ipc.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <stdlib.h>
+#include <ns.h>
+#include <errno.h>
+#include <arch/kbd.h>
+#include <kbd.h>
+#include <key_buffer.h>
+#include <fifo.h>
+
+#define NAME "KBD"
+
+#define KBD_REQUEST_MAX 32 /**< Maximum requests buffered until keypress */
+
+int main(int argc, char **argv)
+{
+	ipc_call_t call;
+	ipc_callid_t callid;
+	char connected = 0;
+	int res;
+	int c;
+	ipcarg_t phonead;
+	
+	ipcarg_t retval, arg1, arg2;
+	
+	fifo_count_t callers_counter = 0;
+	
+	FIFO_INITIALIZE_STATIC(callers_buffer, ipc_callid_t, KBD_REQUEST_MAX);
+
+	printf("Uspace kbd service started.\n");
+
+	/* Initialize arch dependent parts */
+	if (!(res = kbd_arch_init())) {
+			printf("Kbd registration failed with retval %d.\n", res);
+			return -1;
+			};
+	
+	/* Initialize key buffer */
+	key_buffer_init();
+	
+	/* Register service at nameserver */
+	printf("%s: Registering at naming service.\n", NAME);
+
+	if ((res = ipc_connect_to_me(PHONE_NS, 30, 60, &phonead)) != 0) {
+		printf("%s: Error: Registering at naming service failed.\n", NAME);
+		return -1;
+	};
+	
+	while (1) {
+		callid = ipc_wait_for_call(&call, 0);
+	//	printf("%s:Call phone=%lX..", NAME, call.in_phone_hash);
+		switch (IPC_GET_METHOD(call)) {
+		case IPC_M_PHONE_HUNGUP:
+			if (connected) {
+				if (--connected == 0) {
+					callers_counter = 0;
+					callers_buffer.head = callers_buffer.tail = 0;
+					key_buffer_free();	
+				}
+			}
+			
+			printf("%s: Phone hung up.\n", NAME);
+			retval = 0;
+			break;
+		case IPC_M_CONNECT_TO_ME:
+			printf("%s: Somebody connecting phid=%zd.\n", NAME, IPC_GET_ARG3(call));
+			retval = 0;
+			break;
+		case IPC_M_CONNECT_ME_TO:
+		//	printf("%s: Connect me (%P) to: %zd\n",NAME, IPC_GET_ARG3(call), IPC_GET_ARG1(call));
+			if (connected) {
+				retval = ELIMIT;
+			} else {
+				retval = 0;
+				connected = 1;
+			}
+			break;
+		case IPC_M_INTERRUPT:
+			if (connected) {
+				kbd_arch_process(IPC_GET_ARG2(call));
+			}
+			//printf("%s: GOT INTERRUPT: %c\n", NAME, IPC_GET_ARG2(call));
+			if (!callers_counter)
+				break;
+			/* Small trick - interrupt does not need answer so we can change callid to caller awaiting key */
+			callers_counter--;
+			callid = fifo_pop(callers_buffer);
+		case KBD_GETCHAR:
+//			printf("%s: Getchar: ", NAME);
+			retval = 0;
+			arg1 = 0;	
+			if (!key_buffer_pop((char *)&arg1)) {
+				if (callers_counter < KBD_REQUEST_MAX) {
+					callers_counter++;
+					fifo_push(callers_buffer, callid);
+				} else {
+					retval = ELIMIT;
+				}
+				continue;
+			};
+			arg2 = 0xbeef;
+		//	printf("GetChar return %c\n", arg1);
+			
+			break;
+		default:
+			printf("%s: Unknown method: %zd\n", NAME, IPC_GET_METHOD(call));
+			retval = ENOENT;
+			break;
+		}
+		if (! (callid & IPC_CALLID_NOTIFICATION)) {
+		//	printf("%s: Answering\n", NAME);
+			ipc_answer(callid, retval, arg1, arg2);
+		}
+	}
+}
Index: kbd/generic/key_buffer.c
===================================================================
--- kbd/generic/key_buffer.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/generic/key_buffer.c	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,79 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <key_buffer.h>
+#include <fifo.h>
+
+#define KBD_BUFFER_SIZE 128
+
+FIFO_INITIALIZE_STATIC(buffer, char, KBD_BUFFER_SIZE);
+fifo_count_t buffer_items;
+
+void key_buffer_free(void)
+{
+	buffer_items = 0;
+	buffer.head = buffer.tail = 0;
+}
+
+void key_buffer_init(void)
+{
+	key_buffer_free();
+}
+
+/** 
+ * @return empty buffer space
+ */
+int key_buffer_available(void)
+{
+	return KBD_BUFFER_SIZE - buffer_items;
+}
+
+void key_buffer_push(char key)
+{
+	/* TODO: somebody may wait for key */
+	if (buffer_items < KBD_BUFFER_SIZE) {
+		fifo_push(buffer, key);
+		buffer_items++;
+	}
+}
+
+/** Pop character from buffer.
+ * @param c
+ * @return zero on empty buffer, nonzero else
+ */
+int key_buffer_pop(char *c)
+{
+	if (buffer_items > 0) {
+		buffer_items--;
+		*c = fifo_pop(buffer);
+		return 1;
+	}
+	return 0;
+}
+
+
Index: kbd/include/arch
===================================================================
--- kbd/include/arch	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/include/arch	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,1 @@
+../arch/ia32/include
Index: kbd/include/kbd.h
===================================================================
--- kbd/include/kbd.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/include/kbd.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __KBD_H__
+#define __KBD_H__
+
+#define KBD_GETCHAR 1024
+
+#endif
+
Index: kbd/include/key_buffer.h
===================================================================
--- kbd/include/key_buffer.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
+++ kbd/include/key_buffer.h	(revision 51d6f807ff440a0a2def34523275bd9c5cdd6493)
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2006 Josef Cejka
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __KEY_BUFFER_H__
+#define __KEY_BUFFER_H__
+
+#include <types.h>
+
+void key_buffer_free(void);
+void key_buffer_init(void);
+int key_buffer_available(void);
+void key_buffer_push(char key);
+int key_buffer_pop(char *c);
+
+#endif
+
