Index: arch/sparc64/Makefile.inc
===================================================================
--- arch/sparc64/Makefile.inc	(revision c1982e45cfd67b998329f3d32f3b52cbbc6caa5b)
+++ arch/sparc64/Makefile.inc	(revision 8d6bc2d55a5723b035ceb3586ac601c79ece9e54)
@@ -62,5 +62,4 @@
 
 ## Compile with support for framebuffer.
-## Mapping of the framebuffer is implemented by a sparc64-specific function.
 #
 
@@ -92,3 +91,4 @@
 	arch/$(ARCH)/src/trap/interrupt.c \
 	arch/$(ARCH)/src/ddi/ddi.c \
-	arch/$(ARCH)/src/drivers/tick.c
+	arch/$(ARCH)/src/drivers/tick.c \
+	arch/$(ARCH)/src/drivers/i8042.c
Index: arch/sparc64/include/drivers/i8042.h
===================================================================
--- arch/sparc64/include/drivers/i8042.h	(revision c1982e45cfd67b998329f3d32f3b52cbbc6caa5b)
+++ arch/sparc64/include/drivers/i8042.h	(revision 8d6bc2d55a5723b035ceb3586ac601c79ece9e54)
@@ -33,5 +33,4 @@
 
 #define KBD_PHYS_ADDRESS	0x1fff8904000ULL
-#define KBD_VIRT_ADDRESS	0x000d0000000ULL
 
 #define STATUS_REG	4
@@ -39,23 +38,29 @@
 #define DATA_REG	6
 
+#define LAST_REG	DATA_REG
+
+extern volatile __u8 *kbd_virt_address;
+
 static inline void i8042_data_write(__u8 data)
 {
-	((volatile __u8 *)(KBD_VIRT_ADDRESS))[DATA_REG] = data;
+	kbd_virt_address[DATA_REG] = data;
 }
 
 static inline __u8 i8042_data_read(void)
 {
-	return ((volatile __u8 *)(KBD_VIRT_ADDRESS))[DATA_REG];
+	return kbd_virt_address[DATA_REG];
 }
 
 static inline __u8 i8042_status_read(void)
 {
-	return ((volatile __u8 *)(KBD_VIRT_ADDRESS))[STATUS_REG];
+	return kbd_virt_address[STATUS_REG];
 }
 
 static inline void i8042_command_write(__u8 command)
 {
-	((volatile __u8 *)(KBD_VIRT_ADDRESS))[COMMAND_REG] = command;
+	kbd_virt_address[COMMAND_REG] = command;
 }
 
+extern void kbd_init(void);
+
 #endif
Index: arch/sparc64/src/console.c
===================================================================
--- arch/sparc64/src/console.c	(revision c1982e45cfd67b998329f3d32f3b52cbbc6caa5b)
+++ arch/sparc64/src/console.c	(revision 8d6bc2d55a5723b035ceb3586ac601c79ece9e54)
@@ -78,8 +78,6 @@
 	stdin = NULL;
 
-	dtlb_insert_mapping(KBD_VIRT_ADDRESS, KBD_PHYS_ADDRESS, PAGESIZE_8K, true, false);
-
+	kbd_init();
 	fb_init(FB_PHYS_ADDRESS, FB_X_RES, FB_Y_RES, FB_COLOR_DEPTH, FB_X_RES * FB_COLOR_DEPTH / 8);
-	i8042_init();
 }
 
Index: arch/sparc64/src/drivers/i8042.c
===================================================================
--- arch/sparc64/src/drivers/i8042.c	(revision 8d6bc2d55a5723b035ceb3586ac601c79ece9e54)
+++ arch/sparc64/src/drivers/i8042.c	(revision 8d6bc2d55a5723b035ceb3586ac601c79ece9e54)
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2006 Jakub Jermar
+ * 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/drivers/i8042.h>
+#include <genarch/i8042/i8042.h>
+#include <arch/types.h>
+#include <arch/mm/page.h>
+
+volatile __u8 *kbd_virt_address = NULL;
+
+void kbd_init()
+{
+	kbd_virt_address = (__u8 *) hw_map(KBD_PHYS_ADDRESS, LAST_REG);
+	i8042_init();
+}
Index: arch/sparc64/src/mm/page.c
===================================================================
--- arch/sparc64/src/mm/page.c	(revision c1982e45cfd67b998329f3d32f3b52cbbc6caa5b)
+++ arch/sparc64/src/mm/page.c	(revision 8d6bc2d55a5723b035ceb3586ac601c79ece9e54)
@@ -32,4 +32,5 @@
 #include <mm/frame.h>
 #include <bitops.h>
+#include <debug.h>
 
 void page_arch_init(void)
@@ -41,4 +42,24 @@
 {
 	unsigned int order;
+	int i;
+
+	struct {
+		int pagesize;
+		size_t increment;
+		count_t count;
+	} sizemap[] = {
+		{ PAGESIZE_8K, 0, 1 },			/* 8K */
+		{ PAGESIZE_8K, PAGE_SIZE, 2 },		/* 16K */
+		{ PAGESIZE_8K, PAGE_SIZE, 4 },		/* 32K */
+		{ PAGESIZE_64K, 0, 1},			/* 64K */
+		{ PAGESIZE_64K, 8*PAGE_SIZE, 2 },	/* 128K */
+		{ PAGESIZE_64K, 8*PAGE_SIZE, 4 },	/* 256K */
+		{ PAGESIZE_512K, 0, 1 },		/* 512K */
+		{ PAGESIZE_512K, 64*PAGE_SIZE, 2 },	/* 1M */
+		{ PAGESIZE_512K, 64*PAGE_SIZE, 4 },	/* 2M */
+		{ PAGESIZE_4M, 0, 1 }			/* 4M */
+	};
+	
+	ASSERT(size <= 4*1024*1024);
 	
 	if (size <= FRAME_SIZE)
@@ -48,7 +69,9 @@
 	
 	__address virtaddr = PA2KA(PFN2ADDR(frame_alloc(order, FRAME_KA)));
-	
-	dtlb_insert_mapping(virtaddr, physaddr, PAGESIZE_512K, true, false);
-	dtlb_insert_mapping(virtaddr + 512 * 1024, physaddr + 512 * 1024, PAGESIZE_512K, true, false);
+
+	for (i = 0; i < sizemap[order].count; i++)
+		dtlb_insert_mapping(virtaddr + i*sizemap[order].increment,
+				    physaddr + i*sizemap[order].increment,
+				    sizemap[order].pagesize, true, false);
 	
 	return virtaddr;
