Index: console/Makefile
===================================================================
--- console/Makefile	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ console/Makefile	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -34,5 +34,5 @@
 include $(LIBC_PREFIX)/Makefile.toolchain 
 
-CFLAGS += -Iinclude -I../kbd/include ../fb
+CFLAGS += -I. -I../kbd/include -I../fb
 
 LIBS = $(LIBC_PREFIX)/libc.a
@@ -43,5 +43,6 @@
 OUTPUT = console
 GENERIC_SOURCES = \
-	console.c 
+	console.c \
+	../kbd/generic/key_buffer.c
 
 ARCH_SOURCES = 
@@ -63,5 +64,5 @@
 
 $(OUTPUT): $(ARCH_OBJECTS) $(GENERIC_OBJECTS) $(LIBS)
-	$(LD) -T $(LIBC_PREFIX)/arch/$(ARCH)/_link.ld $(GENERIC_OBJECTS) $(ARCH_OBJECTS) $(LIBS) $(LFLAGS) -o $@ -Map $(OUTPUT).map
+	$(LD) -T $(LIBC_PREFIX)/arch/$(ARCH)/_link.ld -e __entry_driver $(GENERIC_OBJECTS) $(ARCH_OBJECTS) $(LIBS) $(LFLAGS) -o $@ -Map $(OUTPUT).map
 
 disasm:
Index: console/console.c
===================================================================
--- console/console.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ console/console.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -29,10 +29,51 @@
 
 #include <kbd.h>
+#include <fb.h>
 #include <ipc/ipc.h>
+#include <ipc/fb.h>
 #include <ipc/services.h>
-#include <stdio.h>
 #include <errno.h>
+#include <key_buffer.h>
+#include <console.h>
+
+//#define CONSOLE_COUNT VFB_CONNECTIONS
+#define CONSOLE_COUNT 6
 
 #define NAME "CONSOLE"
+
+typedef struct {
+	keybuffer_t keybuffer;
+	int client_phone;
+	int vfb_number;	/* Not used */
+	int vfb_phone;
+	int used;
+} connection_t;
+
+connection_t connections[CONSOLE_COUNT];
+
+static int find_free_connection() 
+{
+	int i = 0;
+	
+	while (i < CONSOLE_COUNT) {
+		if (connections[i].used == 0)
+			return i;
+		++i;
+	}
+	return CONSOLE_COUNT;
+}
+
+
+static int find_connection(int client_phone) 
+{
+	int i = 0;
+	
+	while (i < CONSOLE_COUNT) {
+		if (connections[i].client_phone == client_phone)
+			return i;
+		++i;
+	}
+	return  CONSOLE_COUNT;
+}
 
 int main(int argc, char *argv[])
@@ -41,17 +82,15 @@
 	ipc_call_t call;
 	ipc_callid_t callid;
-	int phone_kbd, phone_fb;
+	int kbd_phone, fb_phone;
 	ipcarg_t retval, arg1 = 0xdead, arg2 = 0xbeef;
-	
-	printf("Uspace console service started.\n");
-	
+	int i;
+	int active_client = 0;
 	
 	/* Connect to keyboard driver */
 
-	while ((phone_kbd = ipc_connect_me_to(PHONE_NS, SERVICE_KEYBOARD, 0)) < 0) {
+	while ((kbd_phone = ipc_connect_me_to(PHONE_NS, SERVICE_KEYBOARD, 0)) < 0) {
 	};
 	
-	if (ipc_connect_to_me(phone_kbd, SERVICE_CONSOLE, 0, &phonead) != 0) {
-		printf("%s: Error: Registering at naming service failed.\n", NAME);
+	if (ipc_connect_to_me(kbd_phone, SERVICE_CONSOLE, 0, &phonead) != 0) {
 		return -1;
 	};
@@ -59,13 +98,17 @@
 	/* Connect to framebuffer driver */
 	
-	while ((phone_fb = ipc_connect_me_to(PHONE_NS, SERVICE_VIDEO, 0)) < 0) {
-	};
+	for (i = 0; i < CONSOLE_COUNT; i++) {
+		connections[i].used = 0;
+		keybuffer_init(&(connections[i].keybuffer));
+		/* TODO: init key_buffer */
+		while ((connections[i].vfb_phone = ipc_connect_me_to(PHONE_NS, SERVICE_VIDEO, 0)) < 0) {
+				
+ipc_call_async_2(connections[i].vfb_phone, FB_PUTCHAR, 'a', 'b', NULL, (void *)NULL); 
+		}
+	}
 	
+
 	
-	/* Register service at nameserver */
-	printf("%s: Registering at naming service.\n", NAME);
-
 	if (ipc_connect_to_me(PHONE_NS, SERVICE_CONSOLE, 0, &phonead) != 0) {
-		printf("%s: Error: Registering at naming service failed.\n", NAME);
 		return -1;
 	};
@@ -75,18 +118,69 @@
 		switch (IPC_GET_METHOD(call)) {
 			case IPC_M_PHONE_HUNGUP:
-				printf("%s: Phone hung up.\n", NAME);
-				retval = 0;
+				/*FIXME: if its fb or kbd then panic! */
+				/* free connection */
+				if (i = find_connection(IPC_GET_ARG3(call)) < CONSOLE_COUNT) {
+					connections[i].used = 0;
+					 /*TODO: free connection[i].key_buffer; */
+					/* FIXME: active_connection hungup */
+					retval = 0;
+				} else {
+					/*FIXME: No such connection */
+				}
 				break;
 			case IPC_M_CONNECT_ME_TO:
-				printf("%s: Connect me (%P) to: %zd\n",NAME, IPC_GET_ARG3(call), IPC_GET_ARG1(call));
+				
+				/* find first free connection */
+				
+				if ((i = find_free_connection()) == CONSOLE_COUNT) {
+					retval = ELIMIT;
+					break;
+				}
+				
+				connections[i].used = 1;
+				connections[i].client_phone = IPC_GET_ARG3(call);
+				
 				retval = 0;
 				break;
 			case KBD_PUSHCHAR:
-				printf("%s: Push char '%c'.\n", NAME, IPC_GET_ARG1(call));
+				/* got key from keyboard driver */
+				/* find active console */
+				/* if client is awaiting key, send it */
+				/*FIXME: else store key to its buffer */
 				retval = 0;
+				i = IPC_GET_ARG1(call) & 0xff;
+				/* switch to another virtual console */
+				if ((i >= KBD_KEY_F1) && (i < KBD_KEY_F1 + CONSOLE_COUNT)) {
+					active_client = i - KBD_KEY_F1;
+					break;
+				}
+				
+				keybuffer_push(&(connections[active_client].keybuffer), i);
 				
 				break;
+			case CONSOLE_PUTCHAR:
+				/* find sender client */
+				/* ???
+				 * if its active client, send it to vfb
+				 **/
+				/*FIXME: check, if its from active client, .... */
+
+				if ((i = find_connection(IPC_GET_ARG3(call))) == CONSOLE_COUNT) {
+					break;
+				};
+				
+				/* TODO: send message to fb */
+				ipc_call_async_2(connections[i].vfb_phone, FB_PUTCHAR, IPC_GET_ARG1(call), IPC_GET_ARG2(call), NULL, NULL); 
+				
+				break;
+			case CONSOLE_GETCHAR:
+				/* FIXME: */
+				if (!keybuffer_pop(&(connections[active_client].keybuffer), (char *)&arg1)) {
+					/* FIXME: buffer empty -> store request */
+					arg1 = 'X'; /* Only temporary */
+				};
+//ipc_call_async_2(connections[active_client].vfb_phone, FB_PUTCHAR, ' ', arg1, NULL, (void *)NULL); 
+				break;
 			default:
-				printf("%s: Unknown method: %zd\n", NAME, IPC_GET_METHOD(call));
 				retval = ENOENT;
 				break;
Index: console/console.h
===================================================================
--- console/console.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
+++ console/console.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -0,0 +1,36 @@
+/*
+ * 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 __CONSOLE_H__
+#define __CONSOLE_H__
+
+#define CONSOLE_GETCHAR 1025
+#define CONSOLE_PUTCHAR 1027
+
+#endif
+
Index: fb/fb.c
===================================================================
--- fb/fb.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ fb/fb.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -127,5 +127,5 @@
 	int vfb = vfb_no++;
 
-	if (vfb > 9) {
+	if (vfb > VFB_CONNECTIONS) {
 		ipc_answer_fast(iid, ELIMIT, 0,0);
 		return;
@@ -536,5 +536,5 @@
 	
 	
-	if( (graphics_items[item_new]=malloc(sizeof(framebuffer_descriptor_t))) ==NULL) 
+	if( (graphics_items[item_new]=malloc(sizeof(framebuffer_descriptor_t))) == NULL) 
 	{
 		return EFB;
Index: fb/fb.h
===================================================================
--- fb/fb.h	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ fb/fb.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -33,4 +33,6 @@
 #include <arch/types.h>
 
+#define VFB_CONNECTIONS	9
+
 //void fb_init(int item,__address addr, unsigned int x, unsigned int y, unsigned int bpp, unsigned int scan);
 
Index: kbd/Makefile
===================================================================
--- kbd/Makefile	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/Makefile	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -68,5 +68,5 @@
 
 $(OUTPUT): $(ARCH_OBJECTS) $(GENERIC_OBJECTS) $(LIBS)
-	$(LD) -T $(LIBC_PREFIX)/arch/$(ARCH)/_link.ld $(GENERIC_OBJECTS) $(ARCH_OBJECTS) $(LIBS) $(LFLAGS) -o $@ -Map $(OUTPUT).map
+	$(LD) -T $(LIBC_PREFIX)/arch/$(ARCH)/_link.ld -e __entry_driver $(GENERIC_OBJECTS) $(ARCH_OBJECTS) $(LIBS) $(LFLAGS) -o $@ -Map $(OUTPUT).map
 
 disasm:
Index: kbd/arch/ia32/include/kbd.h
===================================================================
--- kbd/arch/ia32/include/kbd.h	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/arch/ia32/include/kbd.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -30,6 +30,8 @@
 #define __ia32_KBD_H__
 
+#include <key_buffer.h>
+
 int kbd_arch_init(void);
-int kbd_arch_process(int scan_code);
+int kbd_arch_process(keybuffer_t *keybuffer, int scan_code);
 
 #endif
Index: kbd/arch/ia32/src/kbd.c
===================================================================
--- kbd/arch/ia32/src/kbd.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/arch/ia32/src/kbd.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -29,5 +29,4 @@
 
 #include <arch/kbd.h>
-#include <key_buffer.h>
 #include <ipc/ipc.h>
 
@@ -80,14 +79,24 @@
 	' ',
 	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 */
+	0x3b, /* 0x3b - F1 */
+//	SPECIAL, /* 0x3b - F1 */
+	0x3c, /* 0x3c - F2 */
+//	SPECIAL, /* 0x3c - F2 */
+	0x3d, /* 0x3d - F3 */
+//	SPECIAL, /* 0x3d - F3 */
+	0x3e, /* 0x3e - F4 */
+//	SPECIAL, /* 0x3e - F4 */
+//	SPECIAL, /* 0x3f - F5 */
+	0x3f, /* 0x3f - F5 */
+//	SPECIAL, /* 0x40 - F6 */
+	0x40, /* 0x40 - F6 */
+//	SPECIAL, /* 0x41 - F7 */
+	0x41, /* 0x41 - F7 */
+//	SPECIAL, /* 0x42 - F8 */
+	0x42, /* 0x42 - F8 */
+//	SPECIAL, /* 0x43 - F9 */
+	0x43, /* 0x43 - F9 */
+//	SPECIAL, /* 0x44 - F10 */
+	0x44, /* 0x44 - F10 */
 	SPECIAL, /* 0x45 - NumLock */
 	SPECIAL, /* 0x46 - ScrollLock */
@@ -160,14 +169,24 @@
 	' ',
 	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 */
+	0x3b, /* 0x3b - F1 */
+	0x3c, /* 0x3c - F2 */
+	0x3d, /* 0x3d - F3 */
+	0x3e, /* 0x3e - F4 */
+	0x3f, /* 0x3f - F5 */
+	0x40, /* 0x40 - F6 */
+	0x41, /* 0x41 - F7 */
+	0x42, /* 0x42 - F8 */
+	0x43, /* 0x43 - F9 */
+	0x44, /* 0x44 - F10 */
+//	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 */
@@ -231,5 +250,5 @@
 };
 
-static int key_released(unsigned char key)
+static int key_released(keybuffer_t *keybuffer, unsigned char key)
 {
 	switch (key) {
@@ -250,5 +269,5 @@
 }
 
-static int key_pressed(unsigned char key)
+static int key_pressed(keybuffer_t *keybuffer, unsigned char key)
 {
 	char *map = sc_primary_map;
@@ -268,51 +287,51 @@
 			break;
 		case SC_LEFTARR:
-			if (key_buffer_available() >= 3) {
-				key_buffer_push(0x1b);	
-				key_buffer_push(0x5b);	
-				key_buffer_push(0x44);	
+			if (keybuffer_available(keybuffer) >= 3) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x5b);	
+				keybuffer_push(keybuffer, 0x44);	
 			}
 			break;
 		case SC_RIGHTARR:
-			if (key_buffer_available() >= 3) {
-				key_buffer_push(0x1b);	
-				key_buffer_push(0x5b);	
-				key_buffer_push(0x43);	
+			if (keybuffer_available(keybuffer) >= 3) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x5b);	
+				keybuffer_push(keybuffer, 0x43);	
 			}
 			break;
 		case SC_UPARR:
-			if (key_buffer_available() >= 3) {
-				key_buffer_push(0x1b);	
-				key_buffer_push(0x5b);	
-				key_buffer_push(0x41);	
+			if (keybuffer_available(keybuffer) >= 3) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x5b);	
+				keybuffer_push(keybuffer, 0x41);	
 			}
 			break;
 		case SC_DOWNARR:
-			if (key_buffer_available() >= 3) {
-				key_buffer_push(0x1b);	
-				key_buffer_push(0x5b);	
-				key_buffer_push(0x42);	
+			if (keybuffer_available(keybuffer) >= 3) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x5b);	
+				keybuffer_push(keybuffer, 0x42);	
 			}
 			break;
 		case SC_HOME:
-			if (key_buffer_available() >= 3) {
-				key_buffer_push(0x1b);	
-				key_buffer_push(0x4f);	
-				key_buffer_push(0x48);	
+			if (keybuffer_available(keybuffer) >= 3) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x4f);	
+				keybuffer_push(keybuffer, 0x48);	
 			}
 			break;
 		case SC_END:
-			if (key_buffer_available() >= 3) {
-				key_buffer_push(0x1b);	
-				key_buffer_push(0x4f);	
-				key_buffer_push(0x46);	
+			if (keybuffer_available(keybuffer) >= 3) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x4f);	
+				keybuffer_push(keybuffer, 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);	
+			if (keybuffer_available(keybuffer) >= 4) {
+				keybuffer_push(keybuffer, 0x1b);	
+				keybuffer_push(keybuffer, 0x5b);	
+				keybuffer_push(keybuffer, 0x33);	
+				keybuffer_push(keybuffer, 0x7e);	
 			}
 			break;
@@ -325,5 +344,5 @@
 			if (shift)
 				map = sc_secondary_map;
-			key_buffer_push(map[key]);	
+			keybuffer_push(keybuffer, map[key]);	
 			break;
 	}
@@ -338,11 +357,11 @@
 }
 
-int kbd_arch_process(int scan_code)
+int kbd_arch_process(keybuffer_t *keybuffer, int scan_code)
 {
 	if (scan_code != IGNORE_CODE) {
 		if (scan_code & KEY_RELEASE)
-			key_released(scan_code ^ KEY_RELEASE);
+			key_released(keybuffer, scan_code ^ KEY_RELEASE);
 		else
-			key_pressed(scan_code);
+			key_pressed(keybuffer, scan_code);
 	}
 	return 	1;
Index: kbd/arch/mips32/include/kbd.h
===================================================================
--- kbd/arch/mips32/include/kbd.h	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/arch/mips32/include/kbd.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -30,6 +30,8 @@
 #define __mips32_KBD_H__
 
+#include <key_buffer.h>
+
 int kbd_arch_init(void);
-int kbd_arch_process(int scan_code);
+int kbd_arch_process(keybuffer_t *keybuffer, int scan_code);
 
 #endif
Index: kbd/arch/mips32/src/kbd.c
===================================================================
--- kbd/arch/mips32/src/kbd.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/arch/mips32/src/kbd.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -29,5 +29,4 @@
 #include <arch/kbd.h>
 #include <ipc/ipc.h>
-#include <key_buffer.h>
 
 irq_cmd_t msim_cmds[1] = {
@@ -46,7 +45,7 @@
 }
 
-int kbd_arch_process(int scan_code)
+int kbd_arch_process(keybuffer_t *keybuffer, int scan_code)
 {
-	key_buffer_push(scan_code);
+	keybuffer_push(keybuffer, scan_code);
 	return 	1;
 }
Index: kbd/generic/kbd.c
===================================================================
--- kbd/generic/kbd.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/generic/kbd.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -49,23 +49,23 @@
 	int phoneid;
 	char connected = 0;
-	
+	keybuffer_t keybuffer;	
 	ipcarg_t retval, arg1, arg2;
 
-	printf("Uspace kbd service started.\n");
+//	printf("Uspace kbd service started.\n");
 
 	/* Initialize arch dependent parts */
 	if (!(res = kbd_arch_init())) {
-			printf("Kbd registration failed with retval %d.\n", res);
+//			printf("Kbd registration failed with retval %d.\n", res);
 			return -1;
 			};
 	
 	/* Initialize key buffer */
-	key_buffer_init();
+	keybuffer_init(&keybuffer);
 	
 	/* Register service at nameserver */
-	printf("%s: Registering at naming service.\n", NAME);
+//	printf("%s: Registering at naming service.\n", NAME);
 
 	if ((res = ipc_connect_to_me(PHONE_NS, SERVICE_KEYBOARD, 0, &phonead)) != 0) {
-		printf("%s: Error: Registering at naming service failed.\n", NAME);
+//		printf("%s: Error: Registering at naming service failed.\n", NAME);
 		return -1;
 	};
@@ -76,5 +76,5 @@
 		switch (IPC_GET_METHOD(call)) {
 			case IPC_M_PHONE_HUNGUP:
-				printf("%s: Phone hung up.\n", NAME);
+//				printf("%s: Phone hung up.\n", NAME);
 				connected = 0;
 				retval = 0;
@@ -98,5 +98,5 @@
 				if (connected) {
 					/* recode to ASCII - one interrupt can produce more than one code so result is stored in fifo */
-					kbd_arch_process(IPC_GET_ARG2(call));
+					kbd_arch_process(&keybuffer, IPC_GET_ARG2(call));
 
 					//printf("%s: GOT INTERRUPT: %c\n", NAME, key);
@@ -107,18 +107,18 @@
 					retval = 0;
 
-					while (!key_buffer_empty()) {
-						if (!key_buffer_pop((char *)&arg1)) {
-							printf("%s: KeyBuffer is empty but it should not be.\n");
+					while (!keybuffer_empty(&keybuffer)) {
+						if (!keybuffer_pop(&keybuffer, (char *)&arg1)) {
+//							printf("%s: KeyBuffer is empty but it should not be.\n");
 							break;
 						}
 						/*FIXME: detection of closed connection */
-						ipc_call_async(phoneid, KBD_PUSHCHAR, arg1, 0, NULL);
+						ipc_call_async(phoneid, KBD_PUSHCHAR, arg1, NULL, NULL);
 					}
 
 				}
-				printf("%s: Interrupt processed.\n", NAME);
+//				printf("%s: Interrupt processed.\n", NAME);
 				break;
 			default:
-				printf("%s: Unknown method: %zd\n", NAME, IPC_GET_METHOD(call));
+//				printf("%s: Unknown method: %zd\n", NAME, IPC_GET_METHOD(call));
 				retval = ENOENT;
 				break;
Index: kbd/generic/key_buffer.c
===================================================================
--- kbd/generic/key_buffer.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/generic/key_buffer.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -28,17 +28,12 @@
 
 #include <key_buffer.h>
-#include <libadt/fifo.h>
-
-#define KBD_BUFFER_SIZE 128 /**< Size of buffer for pressed keys */
-
-FIFO_INITIALIZE_STATIC(buffer, char, KBD_BUFFER_SIZE);	/**< Fifo for storing pressed keys */
-fifo_count_t buffer_items;	/**< Counter of used items for prevent fifo overflow */
 
 /** Clear key buffer.
  */
-void key_buffer_free(void)
+void keybuffer_free(keybuffer_t *keybuffer) 
 {
-	buffer_items = 0;
-	buffer.head = buffer.tail = 0;
+
+	keybuffer->items = 0;
+	keybuffer->head = keybuffer->tail = keybuffer->items = 0;
 }
 
@@ -46,7 +41,7 @@
  *
  */
-void key_buffer_init(void)
+void keybuffer_init(keybuffer_t *keybuffer)
 {
-	key_buffer_free();
+	keybuffer_free(keybuffer);
 }
 
@@ -56,7 +51,7 @@
  * @return empty buffer space
  */
-int key_buffer_available(void)
+int keybuffer_available(keybuffer_t *keybuffer)
 {
-	return KBD_BUFFER_SIZE - buffer_items;
+	return KEYBUFFER_SIZE - keybuffer->items;
 }
 
@@ -64,7 +59,7 @@
  * @return nonzero, if buffer is not empty.
  */
-int key_buffer_empty(void)
+int keybuffer_empty(keybuffer_t *keybuffer)
 {
-	return (buffer_items == 0);
+	return (keybuffer->items == 0);
 }
 
@@ -73,9 +68,9 @@
  * @param key code of stored key
  */
-void key_buffer_push(char key)
+void keybuffer_push(keybuffer_t *keybuffer, char key)
 {
-	if (buffer_items < KBD_BUFFER_SIZE) {
-		fifo_push(buffer, key);
-		buffer_items++;
+	if (keybuffer->items < KEYBUFFER_SIZE) {
+		keybuffer->fifo[keybuffer->tail = (keybuffer->tail + 1) < keybuffer->items ? (keybuffer->tail + 1) : 0] = (key);
+		keybuffer->items++;
 	}
 }
@@ -85,9 +80,9 @@
  * @return zero on empty buffer, nonzero else
  */
-int key_buffer_pop(char *c)
+int keybuffer_pop(keybuffer_t *keybuffer, char *c)
 {
-	if (buffer_items > 0) {
-		buffer_items--;
-		*c = fifo_pop(buffer);
+	if (keybuffer->items > 0) {
+		keybuffer->items--;
+		*c = keybuffer->fifo[keybuffer->head = (keybuffer->head + 1) < keybuffer->items ? (keybuffer->head + 1) : 0];
 		return 1;
 	}
Index: kbd/include/kbd.h
===================================================================
--- kbd/include/kbd.h	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/include/kbd.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -32,4 +32,17 @@
 #define KBD_PUSHCHAR 1024
 
+#define KBD_KEY_F1	0x3b
+#define KBD_KEY_F2	0x3c
+#define KBD_KEY_F3	0x3d
+#define KBD_KEY_F4	0x3e
+#define KBD_KEY_F5	0x3f
+#define KBD_KEY_F6	0x40
+#define KBD_KEY_F7	0x41
+#define KBD_KEY_F8	0x42
+#define KBD_KEY_F9	0x43
+#define KBD_KEY_F10	0x44
+#define KBD_KEY_F11	0x45
+#define KBD_KEY_F12	0x46
+
 #endif
 
Index: kbd/include/key_buffer.h
===================================================================
--- kbd/include/key_buffer.h	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ kbd/include/key_buffer.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -32,10 +32,19 @@
 #include <types.h>
 
-void key_buffer_free(void);
-void key_buffer_init(void);
-int key_buffer_available(void);
-int key_buffer_empty(void);
-void key_buffer_push(char key);
-int key_buffer_pop(char *c);
+#define KEYBUFFER_SIZE 128 /**< Size of buffer for pressed keys */
+
+typedef struct {
+	char fifo[KEYBUFFER_SIZE];
+	unsigned long head;
+	unsigned long tail;
+	unsigned long items;
+} keybuffer_t;
+
+void keybuffer_free(keybuffer_t *keybuffer);
+void keybuffer_init(keybuffer_t *keybuffer);
+int keybuffer_available(keybuffer_t *keybuffer);
+int keybuffer_empty(keybuffer_t *keybuffer);
+void keybuffer_push(keybuffer_t *keybuffer, char key);
+int keybuffer_pop(keybuffer_t *keybuffer, char *c);
 
 #endif
Index: libc/Makefile
===================================================================
--- libc/Makefile	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ libc/Makefile	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -32,4 +32,5 @@
 LIBC_PREFIX = .
 SOFTINT_PREFIX = ../softint
+CONSOLE_PREFIX = ../console
 
 ## Setup toolchain
@@ -37,4 +38,6 @@
 
 include $(LIBC_PREFIX)/Makefile.toolchain
+
+CFLAGS += -I$(CONSOLE_PREFIX)
 
 ## Sources
Index: libc/generic/io/stream.c
===================================================================
--- libc/generic/io/stream.c	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ libc/generic/io/stream.c	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -8,4 +8,5 @@
 #include <ipc/fb.h>
 #include <ipc/services.h>
+#include <console.h>
 
 #define FDS 32
@@ -17,10 +18,5 @@
 } stream_t;
 
-
-typedef struct vfb_descriptor_t {
-	int phone;
-	int vfb;
-} vfb_descriptor_t;
-
+int console_phone = -1;
 
 stream_t streams[FDS] = {{0, 0, 0}};
@@ -33,15 +29,25 @@
 }*/
 
-static void vfb_send_char(vfb_descriptor_t *d, char c)
+static ssize_t write_stderr(void *param, const void *buf, size_t count)
+{
+	return count;
+	//return (ssize_t) __SYSCALL3(SYS_IO, 1, (sysarg_t) buf, (sysarg_t) count);
+}
+
+static char read_stdin(void)
 {
 	ipcarg_t r0,r1;
-	ipc_call_sync_2(d->phone, FB_PUTCHAR, d->vfb, c, &r0, &r1);
+	ipc_call_sync_2(console_phone, CONSOLE_GETCHAR, 0, 0, &r0, &r1);
+	
+	return r0;
+	//return (ssize_t) __SYSCALL3(SYS_IO, 1, (sysarg_t) buf, (sysarg_t) count);
 }
-				
-static ssize_t write_vfb(void *param, const void *buf, size_t count)
+static ssize_t write_stdout(void *param, const void *buf, size_t count)
 {
 	int i;
+	ipcarg_t r0,r1;
+
 	for (i = 0; i < count; i++)
-		vfb_send_char((vfb_descriptor_t *) param, ((char *) buf)[i]);
+		ipc_call_sync_2(console_phone, CONSOLE_PUTCHAR, 0, ((const char *)buf)[i], &r0, &r1);
 	
 	return count;
@@ -50,36 +56,39 @@
 
 
-static ssize_t write_stderr(void *param, const void *buf, size_t count)
-{
-	return count;
-	//return (ssize_t) __SYSCALL3(SYS_IO, 1, (sysarg_t) buf, (sysarg_t) count);
-}
 
-
-stream_t open_vfb(void)
+static stream_t open_stdin(void)
 {
 	stream_t stream;
-	vfb_descriptor_t *vfb;
 	int phoneid;
 	int res;
-	ipcarg_t vfb_no;
 	
-	while ((phoneid = ipc_connect_me_to(PHONE_NS, SERVICE_VIDEO, 0)) < 0) {
-		volatile int a;
-		
-		for (a = 0; a < 1048576; a++);
+	if (console_phone < 0) {
+		while ((console_phone = ipc_connect_me_to(PHONE_NS, SERVICE_CONSOLE, 0)) < 0) {
+			volatile int a;
+			for (a = 0; a < 1048576; a++);
+		}
 	}
 	
-	ipc_call_sync(phoneid, FB_GET_VFB, 0, &vfb_no);
-	vfb = malloc(sizeof(vfb_descriptor_t));
-	
-	vfb->phone = phoneid;
-	vfb->vfb = vfb_no;
-	
-	stream.w = write_vfb;
-	stream.param = vfb;
+	stream.r = read_stdin;
+	stream.param = 0;
 	return stream;
 }
 
+static stream_t open_stdout(void)
+{
+	stream_t stream;
+	int res;
+	
+	if (console_phone < 0) {
+		while ((console_phone = ipc_connect_me_to(PHONE_NS, SERVICE_CONSOLE, 0)) < 0) {
+			volatile int a;
+			for (a = 0; a < 1048576; a++);
+		}
+	}
+	
+	stream.w = write_stdout;
+	stream.param = 0;
+	return stream;
+}
 
 fd_t open(const char *fname, int flags)
@@ -93,5 +102,5 @@
 	
 	if (!strcmp(fname, "stdin")) {
-		streams[c].r = (preadfn_t)1;
+		streams[c] = open_stdin();
 		return c;
 	}
@@ -100,5 +109,5 @@
 		//streams[c].w = write_stdout;
 		//return c;
-		streams[c] = open_vfb();
+		streams[c] = open_stdout();
 		return c;
 	}
Index: libc/include/io/stream.h
===================================================================
--- libc/include/io/stream.h	(revision f25b73d69b88ecc993955369731abb88eb39810e)
+++ libc/include/io/stream.h	(revision 79460ae08ef89a29aa03f465592f472e382429b9)
@@ -8,5 +8,5 @@
 
 typedef ssize_t (*pwritefn_t)(void *, const void *, size_t);
-typedef ssize_t (*preadfn_t)(void);
+typedef char (*preadfn_t)(void);
 
 fd_t open(const char *fname, int flags);
