Merge with rsync://rsync.kernel.org/pub/scm/linux/kernel/git/torvalds/linux-2.6.git
diff --git a/CREDITS b/CREDITS
index d65ffe5..2993348 100644
--- a/CREDITS
+++ b/CREDITS
@@ -1880,6 +1880,13 @@
 S: D-91080 Uttenreuth
 S: Germany
 
+N: Jaya Kumar
+E: jayalk@intworks.biz
+W: http://www.intworks.biz
+D: Arc monochrome LCD framebuffer driver, x86 reboot fixups
+S: Gurgaon, India
+S: Kuala Lumpur, Malaysia
+
 N: Gabor Kuti
 M: seasons@falcon.sch.bme.hu
 M: seasons@makosteszta.sote.hu
diff --git a/Documentation/fb/intelfb.txt b/Documentation/fb/intelfb.txt
new file mode 100644
index 0000000..c12d39a
--- /dev/null
+++ b/Documentation/fb/intelfb.txt
@@ -0,0 +1,135 @@
+Intel 830M/845G/852GM/855GM/865G/915G Framebuffer driver
+================================================================
+
+A. Introduction
+	This is a framebuffer driver for various Intel 810/815 compatible
+graphics devices.  These would include:
+
+	Intel 830M
+	Intel 810E845G
+	Intel 852GM
+	Intel 855GM
+	Intel 865G
+	Intel 915G
+
+B.  List of available options
+
+   a. "video=intelfb"
+	enables the intelfb driver
+
+	Recommendation: required
+
+   b. "mode=<xres>x<yres>[-<bpp>][@<refresh>]"
+	select mode
+
+	Recommendation: user preference
+	(default = 1024x768-32@70)
+
+   c. "vram=<value>"
+	select amount of system RAM in MB to allocate for the video memory
+	if not enough RAM was already allocated by the BIOS.
+
+	Recommendation: 1 - 4 MB.
+	(default = 4 MB)
+
+   d. "voffset=<value>"
+        select at what offset in MB of the logical memory to allocate the
+	framebuffer memory.  The intent is to avoid the memory blocks
+	used by standard graphics applications (XFree86). Depending on your
+        usage, adjust the value up or down, (0 for maximum usage, 63/127 MB
+        for the least amount).  Note, an arbitrary setting may conflict
+        with XFree86.
+
+	Recommendation: do not set
+	(default = 48 MB)
+
+   e. "accel"
+	enable text acceleration.  This can be enabled/reenabled anytime
+	by using 'fbset -accel true/false'.
+
+	Recommendation: enable
+	(default = set)
+
+   f. "hwcursor"
+	enable cursor acceleration.
+
+	Recommendation: enable
+	(default = set)
+
+   g. "mtrr"
+	enable MTRR.  This allows data transfers to the framebuffer memory
+	to occur in bursts which can significantly increase performance.
+	Not very helpful with the intel chips because of 'shared memory'.
+
+	Recommendation: set
+	(default = set)
+
+   h. "fixed"
+	disable mode switching.
+
+	Recommendation: do not set
+	(default = not set)
+
+   The binary parameters can be unset with a "no" prefix, example "noaccel".
+   The default parameter (not named) is the mode.
+
+C. Kernel booting
+
+Separate each option/option-pair by commas (,) and the option from its value
+with an equals sign (=) as in the following:
+
+video=i810fb:option1,option2=value2
+
+Sample Usage
+------------
+
+In /etc/lilo.conf, add the line:
+
+append="video=intelfb:800x600-32@75,accel,hwcursor,vram=8"
+
+This will initialize the framebuffer to 800x600 at 32bpp and 75Hz. The
+framebuffer will use 8 MB of System RAM. hw acceleration of text and cursor
+will be enabled.
+
+D.  Module options
+
+	The module parameters are essentially similar to the kernel
+parameters. The main difference is that you need to include a Boolean value
+(1 for TRUE, and 0 for FALSE) for those options which don't need a value.
+
+Example, to enable MTRR, include "mtrr=1".
+
+Sample Usage
+------------
+
+Using the same setup as described above, load the module like this:
+
+	modprobe intelfb mode=800x600-32@75 vram=8 accel=1 hwcursor=1
+
+Or just add the following to /etc/modprobe.conf
+
+	options intelfb mode=800x600-32@75 vram=8 accel=1 hwcursor=1
+
+and just do a
+
+	modprobe intelfb
+
+
+E.  Acknowledgment:
+
+	1.  Geert Uytterhoeven - his excellent howto and the virtual
+                                 framebuffer driver code made this possible.
+
+	2.  Jeff Hartmann for his agpgart code.
+
+	3.  David Dawes for his original kernel 2.4 code.
+
+	4.  The X developers.  Insights were provided just by reading the
+	    XFree86 source code.
+
+	5.  Antonino A. Daplas for his inspiring i810fb driver.
+
+	6.  Andrew Morton for his kernel patches maintenance.
+
+###########################
+Sylvain
diff --git a/Documentation/filesystems/isofs.txt b/Documentation/filesystems/isofs.txt
index f64a105..424585f 100644
--- a/Documentation/filesystems/isofs.txt
+++ b/Documentation/filesystems/isofs.txt
@@ -26,7 +26,11 @@
   mode=xxx      Sets the permissions on files to xxx
   nojoliet      Ignore Joliet extensions if they are present.
   norock        Ignore Rock Ridge extensions if they are present.
-  unhide        Show hidden files.
+  hide		Completely strip hidden files from the file system.
+  showassoc	Show files marked with the 'associated' bit
+  unhide	Deprecated; showing hidden files is now default;
+		If given, it is a synonym for 'showassoc' which will
+		recreate previous unhide behavior
   session=x     Select number of session on multisession CD
   sbsector=xxx  Session begins from sector xxx
 
diff --git a/Documentation/filesystems/tmpfs.txt b/Documentation/filesystems/tmpfs.txt
index 417e309..0d783c5 100644
--- a/Documentation/filesystems/tmpfs.txt
+++ b/Documentation/filesystems/tmpfs.txt
@@ -71,8 +71,8 @@
 to limit this tmpfs instance to that percentage of your physical RAM:
 the default, when neither size nor nr_blocks is specified, is size=50%
 
-If both nr_blocks (or size) and nr_inodes are set to 0, neither blocks
-nor inodes will be limited in that instance.  It is generally unwise to
+If nr_blocks=0 (or size=0), blocks will not be limited in that instance;
+if nr_inodes=0, inodes will not be limited.  It is generally unwise to
 mount with such options, since it allows any user with write access to
 use up all the memory on the machine; but enhances the scalability of
 that instance in a system with many cpus making intensive use of it.
@@ -97,4 +97,4 @@
 Author:
    Christoph Rohland <cr@sap.com>, 1.12.01
 Updated:
-   Hugh Dickins <hugh@veritas.com>, 01 September 2004
+   Hugh Dickins <hugh@veritas.com>, 13 March 2005
diff --git a/Documentation/s390/CommonIO b/Documentation/s390/CommonIO
index a831d9a..59d1166 100644
--- a/Documentation/s390/CommonIO
+++ b/Documentation/s390/CommonIO
@@ -30,7 +30,7 @@
   device numbers (0xabcd or abcd, for 2.4 backward compatibility).
   You can use the 'all' keyword to ignore all devices.
   The '!' operator will cause the I/O-layer to _not_ ignore a device.
-  The order on the command line is not important.
+  The command line is parsed from left to right.
 
   For example, 
 	cio_ignore=0.0.0023-0.0.0042,0.0.4711
@@ -72,13 +72,14 @@
   /proc/cio_ignore; "add <device range>, <device range>, ..." will ignore the
   specified devices.
 
-  Note: Already known devices cannot be ignored.
+  Note: While already known devices can be added to the list of devices to be
+        ignored, there will be no effect on then. However, if such a device
+        disappears and then reappeares, it will then be ignored.
 
-  For example, if device 0.0.abcd is already known and all other devices
-  0.0.a000-0.0.afff are not known,
+  For example,
 	"echo add 0.0.a000-0.0.accc, 0.0.af00-0.0.afff > /proc/cio_ignore"
-  will add 0.0.a000-0.0.abcc, 0.0.abce-0.0.accc and 0.0.af00-0.0.afff to the
-  list of ignored devices and skip 0.0.abcd.
+  will add 0.0.a000-0.0.accc and 0.0.af00-0.0.afff to the list of ignored
+  devices.
 
   The devices can be specified either by bus id (0.0.abcd) or, for 2.4 backward
   compatibilty, by the device number in hexadecimal (0xabcd or abcd).
@@ -98,7 +99,8 @@
 
   - /proc/s390dbf/cio_trace/hex_ascii
     Logs the calling of functions in the common I/O-layer and, if applicable, 
-    which subchannel they were called for.
+    which subchannel they were called for, as well as dumps of some data
+    structures (like irb in an error case).
 
   The level of logging can be changed to be more or less verbose by piping to 
   /proc/s390dbf/cio_*/level a number between 0 and 6; see the documentation on
diff --git a/Documentation/sgi-ioc4.txt b/Documentation/sgi-ioc4.txt
new file mode 100644
index 0000000..876c96a
--- /dev/null
+++ b/Documentation/sgi-ioc4.txt
@@ -0,0 +1,45 @@
+The SGI IOC4 PCI device is a bit of a strange beast, so some notes on
+it are in order.
+
+First, even though the IOC4 performs multiple functions, such as an
+IDE controller, a serial controller, a PS/2 keyboard/mouse controller,
+and an external interrupt mechanism, it's not implemented as a
+multifunction device.  The consequence of this from a software
+standpoint is that all these functions share a single IRQ, and
+they can't all register to own the same PCI device ID.  To make
+matters a bit worse, some of the register blocks (and even registers
+themselves) present in IOC4 are mixed-purpose between these several
+functions, meaning that there's no clear "owning" device driver.
+
+The solution is to organize the IOC4 driver into several independent
+drivers, "ioc4", "sgiioc4", and "ioc4_serial".  Note that there is no
+PS/2 controller driver as this functionality has never been wired up
+on a shipping IO card.
+
+ioc4
+====
+This is the core (or shim) driver for IOC4.  It is responsible for
+initializing the basic functionality of the chip, and allocating
+the PCI resources that are shared between the IOC4 functions.
+
+This driver also provides registration functions that the other
+IOC4 drivers can call to make their presence known.  Each driver
+needs to provide a probe and remove function, which are invoked
+by the core driver at appropriate times.  The interface of these
+IOC4 function probe and remove operations isn't precisely the same
+as PCI device probe and remove operations, but is logically the
+same operation.
+
+sgiioc4
+=======
+This is the IDE driver for IOC4.  Its name isn't very descriptive
+simply for historical reasons (it used to be the only IOC4 driver
+component).  There's not much to say about it other than it hooks
+up to the ioc4 driver via the appropriate registration, probe, and
+remove functions.
+
+ioc4_serial
+===========
+This is the serial driver for IOC4.  There's not much to say about it
+other than it hooks up to the ioc4 driver via the appropriate registration,
+probe, and remove functions.
diff --git a/MAINTAINERS b/MAINTAINERS
index e3f0f3f..0f88a70 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -265,6 +265,11 @@
 M:	acme@conectiva.com.br
 S:	Maintained
 
+ARC FRAMEBUFFER DRIVER
+P:	Jaya Kumar
+M:	jayalk@intworks.biz
+S:	Maintained
+
 ARM26 ARCHITECTURE
 P:	Ian Molton
 M:	spyro@f2s.com
diff --git a/arch/arm/mm/mmap.c b/arch/arm/mm/mmap.c
index 32c4b0e..3de7f84 100644
--- a/arch/arm/mm/mmap.c
+++ b/arch/arm/mm/mmap.c
@@ -73,7 +73,12 @@
 		    (!vma || addr + len <= vma->vm_start))
 			return addr;
 	}
-	start_addr = addr = mm->free_area_cache;
+	if (len > mm->cached_hole_size) {
+	        start_addr = addr = mm->free_area_cache;
+	} else {
+	        start_addr = addr = TASK_UNMAPPED_BASE;
+	        mm->cached_hole_size = 0;
+	}
 
 full_search:
 	if (do_align)
@@ -90,6 +95,7 @@
 			 */
 			if (start_addr != TASK_UNMAPPED_BASE) {
 				start_addr = addr = TASK_UNMAPPED_BASE;
+				mm->cached_hole_size = 0;
 				goto full_search;
 			}
 			return -ENOMEM;
@@ -101,6 +107,8 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
 		addr = vma->vm_end;
 		if (do_align)
 			addr = COLOUR_ALIGN(addr, pgoff);
diff --git a/arch/frv/mm/init.c b/arch/frv/mm/init.c
index 41958f5..7943315 100644
--- a/arch/frv/mm/init.c
+++ b/arch/frv/mm/init.c
@@ -169,7 +169,6 @@
 		struct page *page = &mem_map[pfn];
 
 		ClearPageReserved(page);
-		set_bit(PG_highmem, &page->flags);
 		set_page_count(page, 1);
 		__free_page(page);
 		totalram_pages++;
diff --git a/arch/i386/boot/Makefile b/arch/i386/boot/Makefile
index aa7064a..43cd622 100644
--- a/arch/i386/boot/Makefile
+++ b/arch/i386/boot/Makefile
@@ -48,7 +48,7 @@
 $(obj)/zImage $(obj)/bzImage: $(obj)/bootsect $(obj)/setup \
 			      $(obj)/vmlinux.bin $(obj)/tools/build FORCE
 	$(call if_changed,image)
-	@echo 'Kernel: $@ is ready'
+	@echo 'Kernel: $@ is ready' ' (#'`cat .version`')'
 
 $(obj)/vmlinux.bin: $(obj)/compressed/vmlinux FORCE
 	$(call if_changed,objcopy)
diff --git a/arch/i386/kernel/syscall_table.S b/arch/i386/kernel/syscall_table.S
index 6cd1ed3..d408afa 100644
--- a/arch/i386/kernel/syscall_table.S
+++ b/arch/i386/kernel/syscall_table.S
@@ -251,7 +251,7 @@
 	.long sys_io_submit
 	.long sys_io_cancel
 	.long sys_fadvise64	/* 250 */
-	.long sys_ni_syscall
+	.long sys_set_zone_reclaim
 	.long sys_exit_group
 	.long sys_lookup_dcookie
 	.long sys_epoll_create
diff --git a/arch/i386/kernel/traps.c b/arch/i386/kernel/traps.c
index 00c6341..83c579e 100644
--- a/arch/i386/kernel/traps.c
+++ b/arch/i386/kernel/traps.c
@@ -306,7 +306,7 @@
 	};
 	static int die_counter;
 
-	if (die.lock_owner != _smp_processor_id()) {
+	if (die.lock_owner != raw_smp_processor_id()) {
 		console_verbose();
 		spin_lock_irq(&die.lock);
 		die.lock_owner = smp_processor_id();
diff --git a/arch/i386/lib/delay.c b/arch/i386/lib/delay.c
index 080639f..eb0cdfe 100644
--- a/arch/i386/lib/delay.c
+++ b/arch/i386/lib/delay.c
@@ -34,7 +34,7 @@
 	xloops *= 4;
 	__asm__("mull %0"
 		:"=d" (xloops), "=&a" (d0)
-		:"1" (xloops),"0" (cpu_data[_smp_processor_id()].loops_per_jiffy * (HZ/4)));
+		:"1" (xloops),"0" (cpu_data[raw_smp_processor_id()].loops_per_jiffy * (HZ/4)));
         __delay(++xloops);
 }
 
diff --git a/arch/i386/mm/hugetlbpage.c b/arch/i386/mm/hugetlbpage.c
index 171fc92..3b099f3 100644
--- a/arch/i386/mm/hugetlbpage.c
+++ b/arch/i386/mm/hugetlbpage.c
@@ -18,7 +18,7 @@
 #include <asm/tlb.h>
 #include <asm/tlbflush.h>
 
-static pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pud_t *pud;
@@ -30,7 +30,7 @@
 	return (pte_t *) pmd;
 }
 
-static pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pud_t *pud;
@@ -42,21 +42,6 @@
 	return (pte_t *) pmd;
 }
 
-static void set_huge_pte(struct mm_struct *mm, struct vm_area_struct *vma, struct page *page, pte_t * page_table, int write_access)
-{
-	pte_t entry;
-
-	add_mm_counter(mm, rss, HPAGE_SIZE / PAGE_SIZE);
-	if (write_access) {
-		entry =
-		    pte_mkwrite(pte_mkdirty(mk_pte(page, vma->vm_page_prot)));
-	} else
-		entry = pte_wrprotect(mk_pte(page, vma->vm_page_prot));
-	entry = pte_mkyoung(entry);
-	mk_pte_huge(entry);
-	set_pte(page_table, entry);
-}
-
 /*
  * This function checks for proper alignment of input addr and len parameters.
  */
@@ -69,77 +54,6 @@
 	return 0;
 }
 
-int copy_hugetlb_page_range(struct mm_struct *dst, struct mm_struct *src,
-			struct vm_area_struct *vma)
-{
-	pte_t *src_pte, *dst_pte, entry;
-	struct page *ptepage;
-	unsigned long addr = vma->vm_start;
-	unsigned long end = vma->vm_end;
-
-	while (addr < end) {
-		dst_pte = huge_pte_alloc(dst, addr);
-		if (!dst_pte)
-			goto nomem;
-		src_pte = huge_pte_offset(src, addr);
-		entry = *src_pte;
-		ptepage = pte_page(entry);
-		get_page(ptepage);
-		set_pte(dst_pte, entry);
-		add_mm_counter(dst, rss, HPAGE_SIZE / PAGE_SIZE);
-		addr += HPAGE_SIZE;
-	}
-	return 0;
-
-nomem:
-	return -ENOMEM;
-}
-
-int
-follow_hugetlb_page(struct mm_struct *mm, struct vm_area_struct *vma,
-		    struct page **pages, struct vm_area_struct **vmas,
-		    unsigned long *position, int *length, int i)
-{
-	unsigned long vpfn, vaddr = *position;
-	int remainder = *length;
-
-	WARN_ON(!is_vm_hugetlb_page(vma));
-
-	vpfn = vaddr/PAGE_SIZE;
-	while (vaddr < vma->vm_end && remainder) {
-
-		if (pages) {
-			pte_t *pte;
-			struct page *page;
-
-			pte = huge_pte_offset(mm, vaddr);
-
-			/* hugetlb should be locked, and hence, prefaulted */
-			WARN_ON(!pte || pte_none(*pte));
-
-			page = &pte_page(*pte)[vpfn % (HPAGE_SIZE/PAGE_SIZE)];
-
-			WARN_ON(!PageCompound(page));
-
-			get_page(page);
-			pages[i] = page;
-		}
-
-		if (vmas)
-			vmas[i] = vma;
-
-		vaddr += PAGE_SIZE;
-		++vpfn;
-		--remainder;
-		++i;
-	}
-
-	*length = remainder;
-	*position = vaddr;
-
-	return i;
-}
-
 #if 0	/* This is just for testing */
 struct page *
 follow_huge_addr(struct mm_struct *mm, unsigned long address, int write)
@@ -204,83 +118,15 @@
 }
 #endif
 
-void unmap_hugepage_range(struct vm_area_struct *vma,
-		unsigned long start, unsigned long end)
+void hugetlb_clean_stale_pgtable(pte_t *pte)
 {
-	struct mm_struct *mm = vma->vm_mm;
-	unsigned long address;
-	pte_t pte, *ptep;
+	pmd_t *pmd = (pmd_t *) pte;
 	struct page *page;
 
-	BUG_ON(start & (HPAGE_SIZE - 1));
-	BUG_ON(end & (HPAGE_SIZE - 1));
-
-	for (address = start; address < end; address += HPAGE_SIZE) {
-		ptep = huge_pte_offset(mm, address);
-		if (!ptep)
-			continue;
-		pte = ptep_get_and_clear(mm, address, ptep);
-		if (pte_none(pte))
-			continue;
-		page = pte_page(pte);
-		put_page(page);
-	}
-	add_mm_counter(mm ,rss, -((end - start) >> PAGE_SHIFT));
-	flush_tlb_range(vma, start, end);
-}
-
-int hugetlb_prefault(struct address_space *mapping, struct vm_area_struct *vma)
-{
-	struct mm_struct *mm = current->mm;
-	unsigned long addr;
-	int ret = 0;
-
-	BUG_ON(vma->vm_start & ~HPAGE_MASK);
-	BUG_ON(vma->vm_end & ~HPAGE_MASK);
-
-	spin_lock(&mm->page_table_lock);
-	for (addr = vma->vm_start; addr < vma->vm_end; addr += HPAGE_SIZE) {
-		unsigned long idx;
-		pte_t *pte = huge_pte_alloc(mm, addr);
-		struct page *page;
-
-		if (!pte) {
-			ret = -ENOMEM;
-			goto out;
-		}
-
-		if (!pte_none(*pte))
-			continue;
-
-		idx = ((addr - vma->vm_start) >> HPAGE_SHIFT)
-			+ (vma->vm_pgoff >> (HPAGE_SHIFT - PAGE_SHIFT));
-		page = find_get_page(mapping, idx);
-		if (!page) {
-			/* charge the fs quota first */
-			if (hugetlb_get_quota(mapping)) {
-				ret = -ENOMEM;
-				goto out;
-			}
-			page = alloc_huge_page();
-			if (!page) {
-				hugetlb_put_quota(mapping);
-				ret = -ENOMEM;
-				goto out;
-			}
-			ret = add_to_page_cache(page, mapping, idx, GFP_ATOMIC);
-			if (! ret) {
-				unlock_page(page);
-			} else {
-				hugetlb_put_quota(mapping);
-				free_huge_page(page);
-				goto out;
-			}
-		}
-		set_huge_pte(mm, vma, page, pte, vma->vm_flags & VM_WRITE);
-	}
-out:
-	spin_unlock(&mm->page_table_lock);
-	return ret;
+	page = pmd_page(*pmd);
+	pmd_clear(pmd);
+	dec_page_state(nr_page_table_pages);
+	page_cache_release(page);
 }
 
 /* x86_64 also uses this file */
@@ -294,7 +140,12 @@
 	struct vm_area_struct *vma;
 	unsigned long start_addr;
 
-	start_addr = mm->free_area_cache;
+	if (len > mm->cached_hole_size) {
+	        start_addr = mm->free_area_cache;
+	} else {
+	        start_addr = TASK_UNMAPPED_BASE;
+	        mm->cached_hole_size = 0;
+	}
 
 full_search:
 	addr = ALIGN(start_addr, HPAGE_SIZE);
@@ -308,6 +159,7 @@
 			 */
 			if (start_addr != TASK_UNMAPPED_BASE) {
 				start_addr = TASK_UNMAPPED_BASE;
+				mm->cached_hole_size = 0;
 				goto full_search;
 			}
 			return -ENOMEM;
@@ -316,6 +168,8 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
 		addr = ALIGN(vma->vm_end, HPAGE_SIZE);
 	}
 }
@@ -327,12 +181,17 @@
 	struct mm_struct *mm = current->mm;
 	struct vm_area_struct *vma, *prev_vma;
 	unsigned long base = mm->mmap_base, addr = addr0;
+	unsigned long largest_hole = mm->cached_hole_size;
 	int first_time = 1;
 
 	/* don't allow allocations above current base */
 	if (mm->free_area_cache > base)
 		mm->free_area_cache = base;
 
+	if (len <= largest_hole) {
+	        largest_hole = 0;
+		mm->free_area_cache  = base;
+	}
 try_again:
 	/* make sure it can fit in the remaining address space */
 	if (mm->free_area_cache < len)
@@ -353,13 +212,21 @@
 		 * vma->vm_start, use it:
 		 */
 		if (addr + len <= vma->vm_start &&
-				(!prev_vma || (addr >= prev_vma->vm_end)))
+		            (!prev_vma || (addr >= prev_vma->vm_end))) {
 			/* remember the address as a hint for next time */
-			return (mm->free_area_cache = addr);
-		else
+		        mm->cached_hole_size = largest_hole;
+		        return (mm->free_area_cache = addr);
+		} else {
 			/* pull free_area_cache down to the first hole */
-			if (mm->free_area_cache == vma->vm_end)
+		        if (mm->free_area_cache == vma->vm_end) {
 				mm->free_area_cache = vma->vm_start;
+				mm->cached_hole_size = largest_hole;
+			}
+		}
+
+		/* remember the largest hole we saw so far */
+		if (addr + largest_hole < vma->vm_start)
+		        largest_hole = vma->vm_start - addr;
 
 		/* try just below the current vma->vm_start */
 		addr = (vma->vm_start - len) & HPAGE_MASK;
@@ -372,6 +239,7 @@
 	 */
 	if (first_time) {
 		mm->free_area_cache = base;
+		largest_hole = 0;
 		first_time = 0;
 		goto try_again;
 	}
@@ -382,6 +250,7 @@
 	 * allocations.
 	 */
 	mm->free_area_cache = TASK_UNMAPPED_BASE;
+	mm->cached_hole_size = ~0UL;
 	addr = hugetlb_get_unmapped_area_bottomup(file, addr0,
 			len, pgoff, flags);
 
@@ -389,6 +258,7 @@
 	 * Restore the topdown base:
 	 */
 	mm->free_area_cache = base;
+	mm->cached_hole_size = ~0UL;
 
 	return addr;
 }
diff --git a/arch/i386/mm/init.c b/arch/i386/mm/init.c
index 7a7ea37..8766c77 100644
--- a/arch/i386/mm/init.c
+++ b/arch/i386/mm/init.c
@@ -269,7 +269,6 @@
 {
 	if (page_is_ram(pfn) && !(bad_ppro && page_kills_ppro(pfn))) {
 		ClearPageReserved(page);
-		set_bit(PG_highmem, &page->flags);
 		set_page_count(page, 1);
 		__free_page(page);
 		totalhigh_pages++;
diff --git a/arch/ia64/Kconfig b/arch/ia64/Kconfig
index 3ad2c4a..34e603c 100644
--- a/arch/ia64/Kconfig
+++ b/arch/ia64/Kconfig
@@ -50,6 +50,10 @@
 	bool
 	default y
 
+config IA64_UNCACHED_ALLOCATOR
+	bool
+	select GENERIC_ALLOCATOR
+
 choice
 	prompt "System type"
 	default IA64_GENERIC
@@ -223,7 +227,7 @@
 
 config IA64_SGI_SN_XP
 	tristate "Support communication between SGI SSIs"
-	depends on MSPEC
+	select IA64_UNCACHED_ALLOCATOR
 	help
 	  An SGI machine can be divided into multiple Single System
 	  Images which act independently of each other and have
diff --git a/arch/ia64/configs/sn2_defconfig b/arch/ia64/configs/sn2_defconfig
index 6ff7107..a01bb02 100644
--- a/arch/ia64/configs/sn2_defconfig
+++ b/arch/ia64/configs/sn2_defconfig
@@ -588,6 +588,7 @@
 CONFIG_SERIAL_CORE=y
 CONFIG_SERIAL_CORE_CONSOLE=y
 CONFIG_SERIAL_SGI_L1_CONSOLE=y
+CONFIG_SERIAL_SGI_IOC4=y
 CONFIG_UNIX98_PTYS=y
 CONFIG_LEGACY_PTYS=y
 CONFIG_LEGACY_PTY_COUNT=256
@@ -788,6 +789,11 @@
 # CONFIG_INFINIBAND_IPOIB_DEBUG is not set
 
 #
+# SN Devices
+#
+CONFIG_SGI_IOC4=y
+
+#
 # File systems
 #
 CONFIG_EXT2_FS=y
diff --git a/arch/ia64/defconfig b/arch/ia64/defconfig
index 7539e83..9997ef4 100644
--- a/arch/ia64/defconfig
+++ b/arch/ia64/defconfig
@@ -638,6 +638,7 @@
 CONFIG_SERIAL_CORE=y
 CONFIG_SERIAL_CORE_CONSOLE=y
 CONFIG_SERIAL_SGI_L1_CONSOLE=y
+CONFIG_SERIAL_SGI_IOC4=y
 CONFIG_UNIX98_PTYS=y
 CONFIG_LEGACY_PTYS=y
 CONFIG_LEGACY_PTY_COUNT=256
@@ -943,6 +944,11 @@
 # CONFIG_INFINIBAND_IPOIB_DEBUG is not set
 
 #
+# SN Devices
+#
+CONFIG_SGI_IOC4=y
+
+#
 # File systems
 #
 CONFIG_EXT2_FS=y
diff --git a/arch/ia64/kernel/Makefile b/arch/ia64/kernel/Makefile
index c1a02bb..4c73d8b 100644
--- a/arch/ia64/kernel/Makefile
+++ b/arch/ia64/kernel/Makefile
@@ -20,6 +20,7 @@
 obj-$(CONFIG_PERFMON)		+= perfmon_default_smpl.o
 obj-$(CONFIG_IA64_CYCLONE)	+= cyclone.o
 obj-$(CONFIG_IA64_MCA_RECOVERY)	+= mca_recovery.o
+obj-$(CONFIG_IA64_UNCACHED_ALLOCATOR)	+= uncached.o
 mca_recovery-y			+= mca_drv.o mca_drv_asm.o
 
 # The gate DSO image is built using a special linker script.
diff --git a/arch/ia64/kernel/efi.c b/arch/ia64/kernel/efi.c
index 4a3b1aa..179f230 100644
--- a/arch/ia64/kernel/efi.c
+++ b/arch/ia64/kernel/efi.c
@@ -410,6 +410,38 @@
 }
 
 /*
+ * Walk the EFI memory map to pull out leftover pages in the lower
+ * memory regions which do not end up in the regular memory map and
+ * stick them into the uncached allocator
+ *
+ * The regular walk function is significantly more complex than the
+ * uncached walk which means it really doesn't make sense to try and
+ * marge the two.
+ */
+void __init
+efi_memmap_walk_uc (efi_freemem_callback_t callback)
+{
+	void *efi_map_start, *efi_map_end, *p;
+	efi_memory_desc_t *md;
+	u64 efi_desc_size, start, end;
+
+	efi_map_start = __va(ia64_boot_param->efi_memmap);
+	efi_map_end = efi_map_start + ia64_boot_param->efi_memmap_size;
+	efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+	for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+		md = p;
+		if (md->attribute == EFI_MEMORY_UC) {
+			start = PAGE_ALIGN(md->phys_addr);
+			end = PAGE_ALIGN((md->phys_addr+(md->num_pages << EFI_PAGE_SHIFT)) & PAGE_MASK);
+			if ((*callback)(start, end, NULL) < 0)
+				return;
+		}
+	}
+}
+
+
+/*
  * Look for the PAL_CODE region reported by EFI and maps it using an
  * ITR to enable safe PAL calls in virtual mode.  See IA-64 Processor
  * Abstraction Layer chapter 11 in ADAG
diff --git a/arch/ia64/kernel/entry.S b/arch/ia64/kernel/entry.S
index d99316c..b1d5d3d 100644
--- a/arch/ia64/kernel/entry.S
+++ b/arch/ia64/kernel/entry.S
@@ -1579,7 +1579,7 @@
 	data8 sys_keyctl
 	data8 sys_ni_syscall
 	data8 sys_ni_syscall			// 1275
-	data8 sys_ni_syscall
+	data8 sys_set_zone_reclaim
 	data8 sys_ni_syscall
 	data8 sys_ni_syscall
 	data8 sys_ni_syscall
diff --git a/arch/ia64/kernel/uncached.c b/arch/ia64/kernel/uncached.c
new file mode 100644
index 0000000..490dfc9
--- /dev/null
+++ b/arch/ia64/kernel/uncached.c
@@ -0,0 +1,246 @@
+/*
+ * Copyright (C) 2001-2005 Silicon Graphics, Inc.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of version 2 of the GNU General Public License
+ * as published by the Free Software Foundation.
+ *
+ * A simple uncached page allocator using the generic allocator. This
+ * allocator first utilizes the spare (spill) pages found in the EFI
+ * memmap and will then start converting cached pages to uncached ones
+ * at a granule at a time. Node awareness is implemented by having a
+ * pool of pages per node.
+ */
+
+#include <linux/types.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/slab.h>
+#include <linux/efi.h>
+#include <linux/genalloc.h>
+#include <asm/page.h>
+#include <asm/pal.h>
+#include <asm/system.h>
+#include <asm/pgtable.h>
+#include <asm/atomic.h>
+#include <asm/tlbflush.h>
+#include <asm/sn/arch.h>
+
+#define DEBUG	0
+
+#if DEBUG
+#define dprintk			printk
+#else
+#define dprintk(x...)		do { } while (0)
+#endif
+
+void __init efi_memmap_walk_uc (efi_freemem_callback_t callback);
+
+#define MAX_UNCACHED_GRANULES	5
+static int allocated_granules;
+
+struct gen_pool *uncached_pool[MAX_NUMNODES];
+
+
+static void uncached_ipi_visibility(void *data)
+{
+	int status;
+
+	status = ia64_pal_prefetch_visibility(PAL_VISIBILITY_PHYSICAL);
+	if ((status != PAL_VISIBILITY_OK) &&
+	    (status != PAL_VISIBILITY_OK_REMOTE_NEEDED))
+		printk(KERN_DEBUG "pal_prefetch_visibility() returns %i on "
+		       "CPU %i\n", status, get_cpu());
+}
+
+
+static void uncached_ipi_mc_drain(void *data)
+{
+	int status;
+	status = ia64_pal_mc_drain();
+	if (status)
+		printk(KERN_WARNING "ia64_pal_mc_drain() failed with %i on "
+		       "CPU %i\n", status, get_cpu());
+}
+
+
+static unsigned long
+uncached_get_new_chunk(struct gen_pool *poolp)
+{
+	struct page *page;
+	void *tmp;
+	int status, i;
+	unsigned long addr, node;
+
+	if (allocated_granules >= MAX_UNCACHED_GRANULES)
+		return 0;
+
+	node = poolp->private;
+	page = alloc_pages_node(node, GFP_KERNEL | __GFP_ZERO,
+				IA64_GRANULE_SHIFT-PAGE_SHIFT);
+
+	dprintk(KERN_INFO "get_new_chunk page %p, addr %lx\n",
+		page, (unsigned long)(page-vmem_map) << PAGE_SHIFT);
+
+	/*
+	 * Do magic if no mem on local node! XXX
+	 */
+	if (!page)
+		return 0;
+	tmp = page_address(page);
+
+	/*
+	 * There's a small race here where it's possible for someone to
+	 * access the page through /dev/mem halfway through the conversion
+	 * to uncached - not sure it's really worth bothering about
+	 */
+	for (i = 0; i < (IA64_GRANULE_SIZE / PAGE_SIZE); i++)
+		SetPageUncached(&page[i]);
+
+	flush_tlb_kernel_range(tmp, tmp + IA64_GRANULE_SIZE);
+
+	status = ia64_pal_prefetch_visibility(PAL_VISIBILITY_PHYSICAL);
+
+	dprintk(KERN_INFO "pal_prefetch_visibility() returns %i on cpu %i\n",
+		status, get_cpu());
+
+	if (!status) {
+		status = smp_call_function(uncached_ipi_visibility, NULL, 0, 1);
+		if (status)
+			printk(KERN_WARNING "smp_call_function failed for "
+			       "uncached_ipi_visibility! (%i)\n", status);
+	}
+
+	if (ia64_platform_is("sn2"))
+		sn_flush_all_caches((unsigned long)tmp, IA64_GRANULE_SIZE);
+	else
+		flush_icache_range((unsigned long)tmp,
+				   (unsigned long)tmp+IA64_GRANULE_SIZE);
+
+	ia64_pal_mc_drain();
+	status = smp_call_function(uncached_ipi_mc_drain, NULL, 0, 1);
+	if (status)
+		printk(KERN_WARNING "smp_call_function failed for "
+		       "uncached_ipi_mc_drain! (%i)\n", status);
+
+	addr = (unsigned long)tmp - PAGE_OFFSET + __IA64_UNCACHED_OFFSET;
+
+	allocated_granules++;
+	return addr;
+}
+
+
+/*
+ * uncached_alloc_page
+ *
+ * Allocate 1 uncached page. Allocates on the requested node. If no
+ * uncached pages are available on the requested node, roundrobin starting
+ * with higher nodes.
+ */
+unsigned long
+uncached_alloc_page(int nid)
+{
+	unsigned long maddr;
+
+	maddr = gen_pool_alloc(uncached_pool[nid], PAGE_SIZE);
+
+	dprintk(KERN_DEBUG "uncached_alloc_page returns %lx on node %i\n",
+		maddr, nid);
+
+	/*
+	 * If no memory is availble on our local node, try the
+	 * remaining nodes in the system.
+	 */
+	if (!maddr) {
+		int i;
+
+		for (i = MAX_NUMNODES - 1; i >= 0; i--) {
+			if (i == nid || !node_online(i))
+				continue;
+			maddr = gen_pool_alloc(uncached_pool[i], PAGE_SIZE);
+			dprintk(KERN_DEBUG "uncached_alloc_page alternate search "
+				"returns %lx on node %i\n", maddr, i);
+			if (maddr) {
+				break;
+			}
+		}
+	}
+
+	return maddr;
+}
+EXPORT_SYMBOL(uncached_alloc_page);
+
+
+/*
+ * uncached_free_page
+ *
+ * Free a single uncached page.
+ */
+void
+uncached_free_page(unsigned long maddr)
+{
+	int node;
+
+	node = nasid_to_cnodeid(NASID_GET(maddr));
+
+	dprintk(KERN_DEBUG "uncached_free_page(%lx) on node %i\n", maddr, node);
+
+	if ((maddr & (0XFUL << 60)) != __IA64_UNCACHED_OFFSET)
+		panic("uncached_free_page invalid address %lx\n", maddr);
+
+	gen_pool_free(uncached_pool[node], maddr, PAGE_SIZE);
+}
+EXPORT_SYMBOL(uncached_free_page);
+
+
+/*
+ * uncached_build_memmap,
+ *
+ * Called at boot time to build a map of pages that can be used for
+ * memory special operations.
+ */
+static int __init
+uncached_build_memmap(unsigned long start, unsigned long end, void *arg)
+{
+	long length;
+	unsigned long vstart, vend;
+	int node;
+
+	length = end - start;
+	vstart = start + __IA64_UNCACHED_OFFSET;
+	vend = end + __IA64_UNCACHED_OFFSET;
+
+	dprintk(KERN_ERR "uncached_build_memmap(%lx %lx)\n", start, end);
+
+	memset((char *)vstart, 0, length);
+
+	node = nasid_to_cnodeid(NASID_GET(start));
+
+	for (; vstart < vend ; vstart += PAGE_SIZE) {
+		dprintk(KERN_INFO "sticking %lx into the pool!\n", vstart);
+		gen_pool_free(uncached_pool[node], vstart, PAGE_SIZE);
+	}
+
+	return 0;
+}
+
+
+static int __init uncached_init(void) {
+	int i;
+
+	for (i = 0; i < MAX_NUMNODES; i++) {
+		if (!node_online(i))
+			continue;
+		uncached_pool[i] = gen_pool_create(0, IA64_GRANULE_SHIFT,
+						   &uncached_get_new_chunk, i);
+	}
+
+	efi_memmap_walk_uc(uncached_build_memmap);
+
+	return 0;
+}
+
+__initcall(uncached_init);
diff --git a/arch/ia64/mm/hugetlbpage.c b/arch/ia64/mm/hugetlbpage.c
index df08ae7..e0a776a 100644
--- a/arch/ia64/mm/hugetlbpage.c
+++ b/arch/ia64/mm/hugetlbpage.c
@@ -24,7 +24,7 @@
 
 unsigned int hpage_shift=HPAGE_SHIFT_DEFAULT;
 
-static pte_t *
+pte_t *
 huge_pte_alloc (struct mm_struct *mm, unsigned long addr)
 {
 	unsigned long taddr = htlbpage_to_page(addr);
@@ -43,7 +43,7 @@
 	return pte;
 }
 
-static pte_t *
+pte_t *
 huge_pte_offset (struct mm_struct *mm, unsigned long addr)
 {
 	unsigned long taddr = htlbpage_to_page(addr);
@@ -67,23 +67,6 @@
 
 #define mk_pte_huge(entry) { pte_val(entry) |= _PAGE_P; }
 
-static void
-set_huge_pte (struct mm_struct *mm, struct vm_area_struct *vma,
-	      struct page *page, pte_t * page_table, int write_access)
-{
-	pte_t entry;
-
-	add_mm_counter(mm, rss, HPAGE_SIZE / PAGE_SIZE);
-	if (write_access) {
-		entry =
-		    pte_mkwrite(pte_mkdirty(mk_pte(page, vma->vm_page_prot)));
-	} else
-		entry = pte_wrprotect(mk_pte(page, vma->vm_page_prot));
-	entry = pte_mkyoung(entry);
-	mk_pte_huge(entry);
-	set_pte(page_table, entry);
-	return;
-}
 /*
  * This function checks for proper alignment of input addr and len parameters.
  */
@@ -99,68 +82,6 @@
 	return 0;
 }
 
-int copy_hugetlb_page_range(struct mm_struct *dst, struct mm_struct *src,
-			struct vm_area_struct *vma)
-{
-	pte_t *src_pte, *dst_pte, entry;
-	struct page *ptepage;
-	unsigned long addr = vma->vm_start;
-	unsigned long end = vma->vm_end;
-
-	while (addr < end) {
-		dst_pte = huge_pte_alloc(dst, addr);
-		if (!dst_pte)
-			goto nomem;
-		src_pte = huge_pte_offset(src, addr);
-		entry = *src_pte;
-		ptepage = pte_page(entry);
-		get_page(ptepage);
-		set_pte(dst_pte, entry);
-		add_mm_counter(dst, rss, HPAGE_SIZE / PAGE_SIZE);
-		addr += HPAGE_SIZE;
-	}
-	return 0;
-nomem:
-	return -ENOMEM;
-}
-
-int
-follow_hugetlb_page(struct mm_struct *mm, struct vm_area_struct *vma,
-		    struct page **pages, struct vm_area_struct **vmas,
-		    unsigned long *st, int *length, int i)
-{
-	pte_t *ptep, pte;
-	unsigned long start = *st;
-	unsigned long pstart;
-	int len = *length;
-	struct page *page;
-
-	do {
-		pstart = start & HPAGE_MASK;
-		ptep = huge_pte_offset(mm, start);
-		pte = *ptep;
-
-back1:
-		page = pte_page(pte);
-		if (pages) {
-			page += ((start & ~HPAGE_MASK) >> PAGE_SHIFT);
-			get_page(page);
-			pages[i] = page;
-		}
-		if (vmas)
-			vmas[i] = vma;
-		i++;
-		len--;
-		start += PAGE_SIZE;
-		if (((start & HPAGE_MASK) == pstart) && len &&
-				(start < vma->vm_end))
-			goto back1;
-	} while (len && start < vma->vm_end);
-	*length = len;
-	*st = start;
-	return i;
-}
-
 struct page *follow_huge_addr(struct mm_struct *mm, unsigned long addr, int write)
 {
 	struct page *page;
@@ -212,81 +133,6 @@
 	free_pgd_range(tlb, addr, end, floor, ceiling);
 }
 
-void unmap_hugepage_range(struct vm_area_struct *vma, unsigned long start, unsigned long end)
-{
-	struct mm_struct *mm = vma->vm_mm;
-	unsigned long address;
-	pte_t *pte;
-	struct page *page;
-
-	BUG_ON(start & (HPAGE_SIZE - 1));
-	BUG_ON(end & (HPAGE_SIZE - 1));
-
-	for (address = start; address < end; address += HPAGE_SIZE) {
-		pte = huge_pte_offset(mm, address);
-		if (pte_none(*pte))
-			continue;
-		page = pte_page(*pte);
-		put_page(page);
-		pte_clear(mm, address, pte);
-	}
-	add_mm_counter(mm, rss, - ((end - start) >> PAGE_SHIFT));
-	flush_tlb_range(vma, start, end);
-}
-
-int hugetlb_prefault(struct address_space *mapping, struct vm_area_struct *vma)
-{
-	struct mm_struct *mm = current->mm;
-	unsigned long addr;
-	int ret = 0;
-
-	BUG_ON(vma->vm_start & ~HPAGE_MASK);
-	BUG_ON(vma->vm_end & ~HPAGE_MASK);
-
-	spin_lock(&mm->page_table_lock);
-	for (addr = vma->vm_start; addr < vma->vm_end; addr += HPAGE_SIZE) {
-		unsigned long idx;
-		pte_t *pte = huge_pte_alloc(mm, addr);
-		struct page *page;
-
-		if (!pte) {
-			ret = -ENOMEM;
-			goto out;
-		}
-		if (!pte_none(*pte))
-			continue;
-
-		idx = ((addr - vma->vm_start) >> HPAGE_SHIFT)
-			+ (vma->vm_pgoff >> (HPAGE_SHIFT - PAGE_SHIFT));
-		page = find_get_page(mapping, idx);
-		if (!page) {
-			/* charge the fs quota first */
-			if (hugetlb_get_quota(mapping)) {
-				ret = -ENOMEM;
-				goto out;
-			}
-			page = alloc_huge_page();
-			if (!page) {
-				hugetlb_put_quota(mapping);
-				ret = -ENOMEM;
-				goto out;
-			}
-			ret = add_to_page_cache(page, mapping, idx, GFP_ATOMIC);
-			if (! ret) {
-				unlock_page(page);
-			} else {
-				hugetlb_put_quota(mapping);
-				page_cache_release(page);
-				goto out;
-			}
-		}
-		set_huge_pte(mm, vma, page, pte, vma->vm_flags & VM_WRITE);
-	}
-out:
-	spin_unlock(&mm->page_table_lock);
-	return ret;
-}
-
 unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr, unsigned long len,
 		unsigned long pgoff, unsigned long flags)
 {
diff --git a/arch/ia64/sn/kernel/xpc_partition.c b/arch/ia64/sn/kernel/xpc_partition.c
index 2c3c4a8..cd7ed73 100644
--- a/arch/ia64/sn/kernel/xpc_partition.c
+++ b/arch/ia64/sn/kernel/xpc_partition.c
@@ -22,6 +22,7 @@
 #include <linux/cache.h>
 #include <linux/mmzone.h>
 #include <linux/nodemask.h>
+#include <asm/uncached.h>
 #include <asm/sn/bte.h>
 #include <asm/sn/intr.h>
 #include <asm/sn/sn_sal.h>
@@ -183,7 +184,7 @@
 	 * memory protections are never restricted.
 	 */
 	if ((amos_page = xpc_vars->amos_page) == NULL) {
-		amos_page = (AMO_t *) mspec_kalloc_page(0);
+		amos_page = (AMO_t *) TO_AMO(uncached_alloc_page(0));
 		if (amos_page == NULL) {
 			dev_err(xpc_part, "can't allocate page of AMOs\n");
 			return NULL;
@@ -200,7 +201,8 @@
 			if (ret != 0) {
 				dev_err(xpc_part, "can't change memory "
 					"protections\n");
-				mspec_kfree_page((unsigned long) amos_page);
+				uncached_free_page(__IA64_UNCACHED_OFFSET |
+						   TO_PHYS((u64) amos_page));
 				return NULL;
 			}
 		}
diff --git a/arch/m32r/Kconfig b/arch/m32r/Kconfig
index 0d90ea5..64c1333 100644
--- a/arch/m32r/Kconfig
+++ b/arch/m32r/Kconfig
@@ -78,6 +78,9 @@
 config PLAT_MAPPI2
        bool "Mappi-II(M3A-ZA36/M3A-ZA52)"
 
+config PLAT_MAPPI3
+       bool "Mappi-III(M3A-2170)"
+
 endchoice
 
 choice
@@ -134,6 +137,7 @@
 	int "Bus Clock [Hz] (integer)"
 	default "70000000" if PLAT_MAPPI
 	default "25000000" if PLAT_USRV
+	default "50000000" if PLAT_MAPPI3
 	default "50000000" if PLAT_M32700UT
 	default "50000000" if PLAT_OPSPUT
 	default "33333333" if PLAT_OAKS32R
@@ -149,7 +153,7 @@
 
 config MEMORY_START
 	hex "Physical memory start address (hex)"
-	default "08000000" if PLAT_MAPPI || PLAT_MAPPI2
+	default "08000000" if PLAT_MAPPI || PLAT_MAPPI2 || PLAT_MAPPI3
 	default "08000000" if PLAT_USRV
 	default "08000000" if PLAT_M32700UT
 	default "08000000" if PLAT_OPSPUT
@@ -157,6 +161,7 @@
 
 config MEMORY_SIZE
 	hex "Physical memory size (hex)"
+	default "08000000" if PLAT_MAPPI3
 	default "04000000" if PLAT_MAPPI || PLAT_MAPPI2
 	default "02000000" if PLAT_USRV
 	default "01000000" if PLAT_M32700UT
diff --git a/arch/m32r/boot/compressed/m32r_sio.c b/arch/m32r/boot/compressed/m32r_sio.c
index bad5475..8f9a572 100644
--- a/arch/m32r/boot/compressed/m32r_sio.c
+++ b/arch/m32r/boot/compressed/m32r_sio.c
@@ -6,6 +6,7 @@
  */
 
 #include <linux/config.h>
+#include <asm/processor.h>
 
 static void putc(char c);
 
@@ -38,16 +39,17 @@
 
 static void putc(char c)
 {
-
-	while ((*BOOT_SIO0STS & 0x3) != 0x3) ;
+	while ((*BOOT_SIO0STS & 0x3) != 0x3)
+		cpu_relax();
 	if (c == '\n') {
 		*BOOT_SIO0TXB = '\r';
-		while ((*BOOT_SIO0STS & 0x3) != 0x3) ;
+		while ((*BOOT_SIO0STS & 0x3) != 0x3)
+			cpu_relax();
 	}
 	*BOOT_SIO0TXB = c;
 }
-#else /* defined(CONFIG_PLAT_M32700UT_Alpha) || defined(CONFIG_PLAT_M32700UT) */
-#ifdef CONFIG_MMU
+#else /* !(CONFIG_PLAT_M32700UT_Alpha) && !(CONFIG_PLAT_M32700UT) */
+#if defined(CONFIG_PLAT_MAPPI2)
 #define SIO0STS	(volatile unsigned short *)(0xa0efd000 + 14)
 #define SIO0TXB	(volatile unsigned short *)(0xa0efd000 + 30)
 #else
@@ -57,11 +59,12 @@
 
 static void putc(char c)
 {
-
-	while ((*SIO0STS & 0x1) == 0) ;
+	while ((*SIO0STS & 0x1) == 0)
+		cpu_relax();
 	if (c == '\n') {
 		*SIO0TXB = '\r';
-		while ((*SIO0STS & 0x1) == 0) ;
+		while ((*SIO0STS & 0x1) == 0)
+			cpu_relax();
 	}
 	*SIO0TXB = c;
 }
diff --git a/arch/m32r/defconfig b/arch/m32r/defconfig
index 417c95b..8530930 100644
--- a/arch/m32r/defconfig
+++ b/arch/m32r/defconfig
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:10:44 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:20:11 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -16,6 +16,7 @@
 CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -28,13 +29,15 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 # CONFIG_IKCONFIG_PROC is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -44,6 +47,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -65,6 +69,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 CONFIG_CHIP_M32700=y
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -268,7 +273,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -393,18 +397,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -414,6 +406,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 CONFIG_VT=y
@@ -465,6 +468,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -508,8 +515,14 @@
 # Graphics support
 #
 CONFIG_FB=y
+# CONFIG_FB_CFB_FILLRECT is not set
+# CONFIG_FB_CFB_COPYAREA is not set
+# CONFIG_FB_CFB_IMAGEBLIT is not set
+# CONFIG_FB_SOFT_CURSOR is not set
+# CONFIG_FB_MACMODES is not set
 # CONFIG_FB_MODE_HELPERS is not set
 # CONFIG_FB_TILEBLITTING is not set
+# CONFIG_FB_S1D13XXX is not set
 # CONFIG_FB_VIRTUAL is not set
 
 #
@@ -543,10 +556,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -719,8 +728,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/kernel/Makefile b/arch/m32r/kernel/Makefile
index cfd690b..6c6b6c3 100644
--- a/arch/m32r/kernel/Makefile
+++ b/arch/m32r/kernel/Makefile
@@ -10,6 +10,7 @@
 obj-$(CONFIG_SMP)		+= smp.o smpboot.o
 obj-$(CONFIG_PLAT_MAPPI)	+= setup_mappi.o io_mappi.o
 obj-$(CONFIG_PLAT_MAPPI2)	+= setup_mappi2.o io_mappi2.o
+obj-$(CONFIG_PLAT_MAPPI3)	+= setup_mappi3.o io_mappi3.o
 obj-$(CONFIG_PLAT_USRV)		+= setup_usrv.o io_usrv.o
 obj-$(CONFIG_PLAT_M32700UT)	+= setup_m32700ut.o io_m32700ut.o
 obj-$(CONFIG_PLAT_OPSPUT)	+= setup_opsput.o io_opsput.o
@@ -17,4 +18,3 @@
 obj-$(CONFIG_PLAT_OAKS32R)	+= setup_oaks32r.o io_oaks32r.o
 
 EXTRA_AFLAGS	:= -traditional
-
diff --git a/arch/m32r/kernel/io_m32700ut.c b/arch/m32r/kernel/io_m32700ut.c
index 371ba904..e545b06 100644
--- a/arch/m32r/kernel/io_m32700ut.c
+++ b/arch/m32r/kernel/io_m32700ut.c
@@ -3,8 +3,8 @@
  *
  *  Typical I/O routines for M32700UT board.
  *
- *  Copyright (c) 2001, 2002  Hiroyuki Kondo, Hirokazu Takata,
- *                            Hitoshi Yamamoto, Takeo Takahashi
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
+ *                           Hitoshi Yamamoto, Takeo Takahashi
  *
  *  This file is subject to the terms and conditions of the GNU General
  *  Public License.  See the file "COPYING" in the main directory of this
@@ -172,64 +172,21 @@
 
 unsigned char _inb_p(unsigned long port)
 {
-	unsigned char  v;
-
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		v = _ne_inb(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		return *(volatile unsigned char *)__port2addr_ata(port);
-	} else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned char b;
-		pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
-		return b;
-	} else
-#endif
-		v = *(volatile unsigned char *)PORT2ADDR(port);
-
+	unsigned char v = _inb(port);
 	delay();
 	return (v);
 }
 
 unsigned short _inw_p(unsigned long port)
 {
-	unsigned short  v;
-
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		v = _ne_inw(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		return *(volatile unsigned short *)__port2addr_ata(port);
-	} else
-#endif
-#if defined(CONFIG_USB)
-	if(port >= 0x340 && port < 0x3a0)
-		return *(volatile unsigned short *)PORT2ADDR_USB(port);
-	else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned short w;
-		pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
-		return w;
-	} else
-#endif
-		v = *(volatile unsigned short *)PORT2ADDR(port);
-
+	unsigned short v = _inw(port);
 	delay();
 	return (v);
 }
 
 unsigned long _inl_p(unsigned long port)
 {
-	unsigned long  v;
-
-	v = *(volatile unsigned long *)PORT2ADDR(port);
+	unsigned long v = _inl(port);
 	delay();
 	return (v);
 }
@@ -287,52 +244,19 @@
 
 void _outb_p(unsigned char b, unsigned long port)
 {
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		_ne_outb(b, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		*(volatile unsigned char *)__port2addr_ata(port) = b;
-	} else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
-	} else
-#endif
-		*(volatile unsigned char *)PORT2ADDR(port) = b;
-
+	_outb(b, port);
 	delay();
 }
 
 void _outw_p(unsigned short w, unsigned long port)
 {
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		_ne_outw(w, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		*(volatile unsigned short *)__port2addr_ata(port) = w;
-	} else
-#endif
-#if defined(CONFIG_USB)
-	if(port >= 0x340 && port < 0x3a0)
-		*(volatile unsigned short *)PORT2ADDR_USB(port) = w;
-	else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
-	} else
-#endif
-		*(volatile unsigned short *)PORT2ADDR(port) = w;
-
+	_outw(w, port);
 	delay();
 }
 
 void _outl_p(unsigned long l, unsigned long port)
 {
-	*(volatile unsigned long *)PORT2ADDR(port) = l;
+	_outl(l, port);
 	delay();
 }
 
diff --git a/arch/m32r/kernel/io_mappi.c b/arch/m32r/kernel/io_mappi.c
index 85688ff..7803316 100644
--- a/arch/m32r/kernel/io_mappi.c
+++ b/arch/m32r/kernel/io_mappi.c
@@ -3,8 +3,8 @@
  *
  *  Typical I/O routines for Mappi board.
  *
- *  Copyright (c) 2001, 2002  Hiroyuki Kondo, Hirokazu Takata,
- *                            Hitoshi Yamamoto
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
+ *                           Hitoshi Yamamoto
  */
 
 #include <linux/config.h>
@@ -130,57 +130,21 @@
 
 unsigned char _inb_p(unsigned long port)
 {
-	unsigned char  v;
-
-	if (port >= 0x300 && port < 0x320)
-		v = _ne_inb(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_PCC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned char b;
-		pcc_ioread(0, port, &b, sizeof(b), 1, 0);
-		return b;
-	} else 	if (port >= M32R_PCC_IOSTART1 && port <= M32R_PCC_IOEND1) {
-		unsigned char b;
-		pcc_ioread(1, port, &b, sizeof(b), 1, 0);
-		return b;
-	} else
-#endif
-		v = *(volatile unsigned char *)PORT2ADDR(port);
-
+	unsigned char v = _inb(port);
 	delay();
 	return (v);
 }
 
 unsigned short _inw_p(unsigned long port)
 {
-	unsigned short  v;
-
-	if (port >= 0x300 && port < 0x320)
-		v = _ne_inw(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_PCC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned short w;
-		pcc_ioread(0, port, &w, sizeof(w), 1, 0);
-		return w;
-	} else 	if (port >= M32R_PCC_IOSTART1 && port <= M32R_PCC_IOEND1) {
-		unsigned short w;
-		pcc_ioread(1, port, &w, sizeof(w), 1, 0);
-		return w;
-	} else
-#endif
-		v = *(volatile unsigned short *)PORT2ADDR(port);
-
+	unsigned short v = _inw(port);
 	delay();
 	return (v);
 }
 
 unsigned long _inl_p(unsigned long port)
 {
-	unsigned long  v;
-
-	v = *(volatile unsigned long *)PORT2ADDR(port);
+	unsigned long v = _inl(port);
 	delay();
 	return (v);
 }
@@ -229,41 +193,19 @@
 
 void _outb_p(unsigned char b, unsigned long port)
 {
-	if (port >= 0x300 && port < 0x320)
-		_ne_outb(b, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_PCC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite(0, port, &b, sizeof(b), 1, 0);
-	} else 	if (port >= M32R_PCC_IOSTART1 && port <= M32R_PCC_IOEND1) {
-		pcc_iowrite(1, port, &b, sizeof(b), 1, 0);
-	} else
-#endif
-		*(volatile unsigned char *)PORT2ADDR(port) = b;
-
+	_outb(b, port);
 	delay();
 }
 
 void _outw_p(unsigned short w, unsigned long port)
 {
-	if (port >= 0x300 && port < 0x320)
-		_ne_outw(w, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_PCC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite(0, port, &w, sizeof(w), 1, 0);
-	} else 	if (port >= M32R_PCC_IOSTART1 && port <= M32R_PCC_IOEND1) {
-		pcc_iowrite(1, port, &w, sizeof(w), 1, 0);
-	} else
-#endif
-		*(volatile unsigned short *)PORT2ADDR(port) = w;
-
+	_outw(w, port);
 	delay();
 }
 
 void _outl_p(unsigned long l, unsigned long port)
 {
-	*(volatile unsigned long *)PORT2ADDR(port) = l;
+	_outl(l, port);
 	delay();
 }
 
diff --git a/arch/m32r/kernel/io_mappi2.c b/arch/m32r/kernel/io_mappi2.c
index 4182cd4..5c03504 100644
--- a/arch/m32r/kernel/io_mappi2.c
+++ b/arch/m32r/kernel/io_mappi2.c
@@ -3,7 +3,7 @@
  *
  *  Typical I/O routines for Mappi2 board.
  *
- *  Copyright (c) 2001-2003  Hiroyuki Kondo, Hirokazu Takata,
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
  *                           Hitoshi Yamamoto, Mamoru Sakugawa
  */
 
@@ -25,7 +25,7 @@
 extern void pcc_ioread_word(int, unsigned long, void *, size_t, size_t, int);
 extern void pcc_iowrite_byte(int, unsigned long, void *, size_t, size_t, int);
 extern void pcc_iowrite_word(int, unsigned long, void *, size_t, size_t, int);
-#endif /* CONFIG_PCMCIA && CONFIG_MAPPI2_CFC */
+#endif /* CONFIG_PCMCIA && CONFIG_M32R_CFC */
 
 #define PORT2ADDR(port)      _port2addr(port)
 #define PORT2ADDR_NE(port)   _port2addr_ne(port)
@@ -169,64 +169,21 @@
 
 unsigned char _inb_p(unsigned long port)
 {
-	unsigned char  v;
-
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		v = _ne_inb(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		return *(volatile unsigned char *)__port2addr_ata(port);
-	} else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned char b;
-		pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
-		return b;
-	} else
-#endif
-		v = *(volatile unsigned char *)PORT2ADDR(port);
-
+	unsigned char v = _inb(port);
 	delay();
 	return (v);
 }
 
 unsigned short _inw_p(unsigned long port)
 {
-	unsigned short  v;
-
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		v = _ne_inw(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		return *(volatile unsigned short *)__port2addr_ata(port);
-	} else
-#endif
-#if defined(CONFIG_USB)
-	if (port >= 0x340 && port < 0x3a0)
-		v = *(volatile unsigned short *)PORT2ADDR_USB(port);
-	else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned short w;
-		pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
-		return w;
-	} else
-#endif
-		v = *(volatile unsigned short *)PORT2ADDR(port);
-
+	unsigned short v = _inw(port);
 	delay();
 	return (v);
 }
 
 unsigned long _inl_p(unsigned long port)
 {
-	unsigned long  v;
-
-	v = *(volatile unsigned long *)PORT2ADDR(port);
+	unsigned long v = _inl(port);
 	delay();
 	return (v);
 }
@@ -284,52 +241,19 @@
 
 void _outb_p(unsigned char b, unsigned long port)
 {
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		_ne_outb(b, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		*(volatile unsigned char *)__port2addr_ata(port) = b;
-	} else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
-	} else
-#endif
-		*(volatile unsigned char *)PORT2ADDR(port) = b;
-
+	_outb(b, port);
 	delay();
 }
 
 void _outw_p(unsigned short w, unsigned long port)
 {
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		_ne_outw(w, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
-	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
-		*(volatile unsigned short *)__port2addr_ata(port) = w;
-	} else
-#endif
-#if defined(CONFIG_USB)
-	  if (port >= 0x340 && port < 0x3a0)
-		*(volatile unsigned short *)PORT2ADDR_USB(port) = w;
-	else
-#endif
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
-	} else
-#endif
-		*(volatile unsigned short *)PORT2ADDR(port) = w;
-
+	_outw(w, port);
 	delay();
 }
 
 void _outl_p(unsigned long l, unsigned long port)
 {
-	*(volatile unsigned long *)PORT2ADDR(port) = l;
+	_outl(l, port);
 	delay();
 }
 
diff --git a/arch/m32r/kernel/io_mappi3.c b/arch/m32r/kernel/io_mappi3.c
new file mode 100644
index 0000000..c80bde6
--- /dev/null
+++ b/arch/m32r/kernel/io_mappi3.c
@@ -0,0 +1,378 @@
+/*
+ *  linux/arch/m32r/kernel/io_mappi3.c
+ *
+ *  Typical I/O routines for Mappi3 board.
+ *
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
+ *                           Hitoshi Yamamoto, Mamoru Sakugawa
+ */
+
+#include <linux/config.h>
+#include <asm/m32r.h>
+#include <asm/page.h>
+#include <asm/io.h>
+#include <asm/byteorder.h>
+
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+#include <linux/types.h>
+
+#define M32R_PCC_IOMAP_SIZE 0x1000
+
+#define M32R_PCC_IOSTART0 0x1000
+#define M32R_PCC_IOEND0   (M32R_PCC_IOSTART0 + M32R_PCC_IOMAP_SIZE - 1)
+
+extern void pcc_ioread_byte(int, unsigned long, void *, size_t, size_t, int);
+extern void pcc_ioread_word(int, unsigned long, void *, size_t, size_t, int);
+extern void pcc_iowrite_byte(int, unsigned long, void *, size_t, size_t, int);
+extern void pcc_iowrite_word(int, unsigned long, void *, size_t, size_t, int);
+#endif /* CONFIG_PCMCIA && CONFIG_M32R_CFC */
+
+#define PORT2ADDR(port)      _port2addr(port)
+#define PORT2ADDR_NE(port)   _port2addr_ne(port)
+#define PORT2ADDR_USB(port)  _port2addr_usb(port)
+
+static inline void *_port2addr(unsigned long port)
+{
+	return (void *)(port + NONCACHE_OFFSET);
+}
+
+#define LAN_IOSTART	0x300
+#define LAN_IOEND	0x320
+
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+static inline void *__port2addr_ata(unsigned long port)
+{
+	static int	dummy_reg;
+
+	switch (port) {
+	case 0x1f0:	return (void *)0xb4002000;
+	case 0x1f1:	return (void *)0xb4012800;
+	case 0x1f2:	return (void *)0xb4012002;
+	case 0x1f3:	return (void *)0xb4012802;
+	case 0x1f4:	return (void *)0xb4012004;
+	case 0x1f5:	return (void *)0xb4012804;
+	case 0x1f6:	return (void *)0xb4012006;
+	case 0x1f7:	return (void *)0xb4012806;
+	case 0x3f6:	return (void *)0xb401200e;
+	default: 	return (void *)&dummy_reg;
+	}
+}
+#endif
+
+static inline void *_port2addr_ne(unsigned long port)
+{
+	return (void *)(port + NONCACHE_OFFSET + 0x10000000);
+}
+
+static inline void *_port2addr_usb(unsigned long port)
+{
+	return (void *)(port + NONCACHE_OFFSET + 0x12000000);
+}
+static inline void delay(void)
+{
+	__asm__ __volatile__ ("push r0; \n\t pop r0;" : : :"memory");
+}
+
+/*
+ * NIC I/O function
+ */
+
+static inline unsigned char _ne_inb(void *portp)
+{
+	return (unsigned char) *(volatile unsigned char *)portp;
+}
+
+static inline unsigned short _ne_inw(void *portp)
+{
+	return (unsigned short)le16_to_cpu(*(volatile unsigned short *)portp);
+}
+
+static inline void _ne_insb(void *portp, void * addr, unsigned long count)
+{
+	unsigned char *buf = addr;
+
+	while (count--)
+		*buf++ = *(volatile unsigned char *)portp;
+}
+
+static inline void _ne_outb(unsigned char b, void *portp)
+{
+	*(volatile unsigned char *)portp = (unsigned char)b;
+}
+
+static inline void _ne_outw(unsigned short w, void *portp)
+{
+	*(volatile unsigned short *)portp = cpu_to_le16(w);
+}
+
+unsigned char _inb(unsigned long port)
+{
+	if (port >= LAN_IOSTART && port < LAN_IOEND)
+		return _ne_inb(PORT2ADDR_NE(port));
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	else if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		return *(volatile unsigned char *)__port2addr_ata(port);
+	}
+#endif
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		unsigned char b;
+		pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
+		return b;
+	} else
+#endif
+	return *(volatile unsigned char *)PORT2ADDR(port);
+}
+
+unsigned short _inw(unsigned long port)
+{
+	if (port >= LAN_IOSTART && port < LAN_IOEND)
+		return _ne_inw(PORT2ADDR_NE(port));
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	else if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		return *(volatile unsigned short *)__port2addr_ata(port);
+	}
+#endif
+#if defined(CONFIG_USB)
+	else if (port >= 0x340 && port < 0x3a0)
+		return *(volatile unsigned short *)PORT2ADDR_USB(port);
+#endif
+
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		unsigned short w;
+		pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
+		return w;
+	} else
+#endif
+	return *(volatile unsigned short *)PORT2ADDR(port);
+}
+
+unsigned long _inl(unsigned long port)
+{
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		unsigned long l;
+		pcc_ioread_word(0, port, &l, sizeof(l), 1, 0);
+		return l;
+	} else
+#endif
+	return *(volatile unsigned long *)PORT2ADDR(port);
+}
+
+unsigned char _inb_p(unsigned long port)
+{
+	unsigned char v = _inb(port);
+	delay();
+	return (v);
+}
+
+unsigned short _inw_p(unsigned long port)
+{
+	unsigned short v = _inw(port);
+	delay();
+	return (v);
+}
+
+unsigned long _inl_p(unsigned long port)
+{
+	unsigned long v = _inl(port);
+	delay();
+	return (v);
+}
+
+void _outb(unsigned char b, unsigned long port)
+{
+	if (port >= LAN_IOSTART && port < LAN_IOEND)
+		_ne_outb(b, PORT2ADDR_NE(port));
+	else
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		*(volatile unsigned char *)__port2addr_ata(port) = b;
+	} else
+#endif
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
+	} else
+#endif
+		*(volatile unsigned char *)PORT2ADDR(port) = b;
+}
+
+void _outw(unsigned short w, unsigned long port)
+{
+	if (port >= LAN_IOSTART && port < LAN_IOEND)
+		_ne_outw(w, PORT2ADDR_NE(port));
+	else
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		*(volatile unsigned short *)__port2addr_ata(port) = w;
+	} else
+#endif
+#if defined(CONFIG_USB)
+	if (port >= 0x340 && port < 0x3a0)
+		*(volatile unsigned short *)PORT2ADDR_USB(port) = w;
+	else
+#endif
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
+	} else
+#endif
+		*(volatile unsigned short *)PORT2ADDR(port) = w;
+}
+
+void _outl(unsigned long l, unsigned long port)
+{
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_iowrite_word(0, port, &l, sizeof(l), 1, 0);
+	} else
+#endif
+	*(volatile unsigned long *)PORT2ADDR(port) = l;
+}
+
+void _outb_p(unsigned char b, unsigned long port)
+{
+	_outb(b, port);
+	delay();
+}
+
+void _outw_p(unsigned short w, unsigned long port)
+{
+	_outw(w, port);
+	delay();
+}
+
+void _outl_p(unsigned long l, unsigned long port)
+{
+	_outl(l, port);
+	delay();
+}
+
+void _insb(unsigned int port, void * addr, unsigned long count)
+{
+	if (port >= LAN_IOSTART && port < LAN_IOEND)
+		_ne_insb(PORT2ADDR_NE(port), addr, count);
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	else if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		unsigned char *buf = addr;
+		unsigned char *portp = __port2addr_ata(port);
+		while (count--)
+			*buf++ = *(volatile unsigned char *)portp;
+	}
+#endif
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_ioread_byte(0, port, (void *)addr, sizeof(unsigned char),
+				count, 1);
+	}
+#endif
+	else {
+		unsigned char *buf = addr;
+		unsigned char *portp = PORT2ADDR(port);
+		while (count--)
+			*buf++ = *(volatile unsigned char *)portp;
+	}
+}
+
+void _insw(unsigned int port, void * addr, unsigned long count)
+{
+	unsigned short *buf = addr;
+	unsigned short *portp;
+
+	if (port >= LAN_IOSTART && port < LAN_IOEND) {
+		portp = PORT2ADDR_NE(port);
+		while (count--)
+			*buf++ = *(volatile unsigned short *)portp;
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	} else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_ioread_word(9, port, (void *)addr, sizeof(unsigned short),
+				count, 1);
+#endif
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	} else if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		portp = __port2addr_ata(port);
+		while (count--)
+			*buf++ = *(volatile unsigned short *)portp;
+#endif
+	} else {
+		portp = PORT2ADDR(port);
+		while (count--)
+			*buf++ = *(volatile unsigned short *)portp;
+	}
+}
+
+void _insl(unsigned int port, void * addr, unsigned long count)
+{
+	unsigned long *buf = addr;
+	unsigned long *portp;
+
+	portp = PORT2ADDR(port);
+	while (count--)
+		*buf++ = *(volatile unsigned long *)portp;
+}
+
+void _outsb(unsigned int port, const void * addr, unsigned long count)
+{
+	const unsigned char *buf = addr;
+	unsigned char *portp;
+
+	if (port >= LAN_IOSTART && port < LAN_IOEND) {
+		portp = PORT2ADDR_NE(port);
+		while (count--)
+			_ne_outb(*buf++, portp);
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	} else if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		portp = __port2addr_ata(port);
+		while (count--)
+			*(volatile unsigned char *)portp = *buf++;
+#endif
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	} else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_iowrite_byte(0, port, (void *)addr, sizeof(unsigned char),
+				 count, 1);
+#endif
+	} else {
+		portp = PORT2ADDR(port);
+		while (count--)
+			*(volatile unsigned char *)portp = *buf++;
+	}
+}
+
+void _outsw(unsigned int port, const void * addr, unsigned long count)
+{
+	const unsigned short *buf = addr;
+	unsigned short *portp;
+
+	if (port >= LAN_IOSTART && port < LAN_IOEND) {
+		portp = PORT2ADDR_NE(port);
+		while (count--)
+			*(volatile unsigned short *)portp = *buf++;
+#if defined(CONFIG_IDE) && !defined(CONFIG_M32R_CFC)
+	} else if ((port >= 0x1f0 && port <=0x1f7) || port == 0x3f6) {
+		portp = __port2addr_ata(port);
+		while (count--)
+			*(volatile unsigned short *)portp = *buf++;
+#endif
+#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
+	} else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
+		pcc_iowrite_word(9, port, (void *)addr, sizeof(unsigned short),
+				 count, 1);
+#endif
+	} else {
+		portp = PORT2ADDR(port);
+		while (count--)
+			*(volatile unsigned short *)portp = *buf++;
+	}
+}
+
+void _outsl(unsigned int port, const void * addr, unsigned long count)
+{
+	const unsigned long *buf = addr;
+	unsigned char *portp;
+
+	portp = PORT2ADDR(port);
+	while (count--)
+		*(volatile unsigned long *)portp = *buf++;
+}
diff --git a/arch/m32r/kernel/io_oaks32r.c b/arch/m32r/kernel/io_oaks32r.c
index 2869647..9997ddd 100644
--- a/arch/m32r/kernel/io_oaks32r.c
+++ b/arch/m32r/kernel/io_oaks32r.c
@@ -3,7 +3,7 @@
  *
  *  Typical I/O routines for OAKS32R board.
  *
- *  Copyright (c) 2001-2004  Hiroyuki Kondo, Hirokazu Takata,
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
  *                           Hitoshi Yamamoto, Mamoru Sakugawa
  */
 
@@ -90,35 +90,21 @@
 
 unsigned char _inb_p(unsigned long port)
 {
-	unsigned char  v;
-
-	if (port >= 0x300 && port < 0x320)
-		v = _ne_inb(PORT2ADDR_NE(port));
-	else
-		v = *(volatile unsigned char *)PORT2ADDR(port);
-
+	unsigned char v = _inb(port);
 	delay();
 	return (v);
 }
 
 unsigned short _inw_p(unsigned long port)
 {
-	unsigned short  v;
-
-	if (port >= 0x300 && port < 0x320)
-		v = _ne_inw(PORT2ADDR_NE(port));
-	else
-		v = *(volatile unsigned short *)PORT2ADDR(port);
-
+	unsigned short v = _inw(port);
 	delay();
 	return (v);
 }
 
 unsigned long _inl_p(unsigned long port)
 {
-	unsigned long  v;
-
-	v = *(volatile unsigned long *)PORT2ADDR(port);
+	unsigned long v = _inl(port);
 	delay();
 	return (v);
 }
@@ -146,27 +132,19 @@
 
 void _outb_p(unsigned char b, unsigned long port)
 {
-	if (port >= 0x300 && port < 0x320)
-		_ne_outb(b, PORT2ADDR_NE(port));
-	else
-		*(volatile unsigned char *)PORT2ADDR(port) = b;
-
+	_outb(b, port);
 	delay();
 }
 
 void _outw_p(unsigned short w, unsigned long port)
 {
-	if (port >= 0x300 && port < 0x320)
-		_ne_outw(w, PORT2ADDR_NE(port));
-	else
-		*(volatile unsigned short *)PORT2ADDR(port) = w;
-
+	_outw(w, port);
 	delay();
 }
 
 void _outl_p(unsigned long l, unsigned long port)
 {
-	*(volatile unsigned long *)PORT2ADDR(port) = l;
+	_outl(l, port);
 	delay();
 }
 
diff --git a/arch/m32r/kernel/io_opsput.c b/arch/m32r/kernel/io_opsput.c
index aaf42f9..e34951e 100644
--- a/arch/m32r/kernel/io_opsput.c
+++ b/arch/m32r/kernel/io_opsput.c
@@ -1,10 +1,10 @@
 /*
- *  linux/arch/m32r/kernel/io_mappi.c
+ *  linux/arch/m32r/kernel/io_opsput.c
  *
  *  Typical I/O routines for OPSPUT board.
  *
- *  Copyright (c) 2001, 2002  Hiroyuki Kondo, Hirokazu Takata,
- *                            Hitoshi Yamamoto, Takeo Takahashi
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
+ *                           Hitoshi Yamamoto, Takeo Takahashi
  *
  *  This file is subject to the terms and conditions of the GNU General
  *  Public License.  See the file "COPYING" in the main directory of this
@@ -98,7 +98,6 @@
 {
 	if (port >= LAN_IOSTART && port < LAN_IOEND)
 		return _ne_inb(PORT2ADDR_NE(port));
-
 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
 	else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
 		unsigned char b;
@@ -118,7 +117,6 @@
 	else if(port >= 0x340 && port < 0x3a0)
 		return *(volatile unsigned short *)PORT2ADDR_USB(port);
 #endif
-
 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
 	else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
 		unsigned short w;
@@ -143,55 +141,21 @@
 
 unsigned char _inb_p(unsigned long port)
 {
-	unsigned char  v;
-
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		v = _ne_inb(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned char b;
-		pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
-		return b;
-	} else
-#endif
-		v = *(volatile unsigned char *)PORT2ADDR(port);
-
+	unsigned char v = _inb(port);
 	delay();
 	return (v);
 }
 
 unsigned short _inw_p(unsigned long port)
 {
-	unsigned short  v;
-
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		v = _ne_inw(PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_USB)
-	if(port >= 0x340 && port < 0x3a0)
-		return *(volatile unsigned short *)PORT2ADDR_USB(port);
-	else
-#endif
-
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		unsigned short w;
-		pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
-		return w;
-	} else
-#endif
-		v = *(volatile unsigned short *)PORT2ADDR(port);
-
+	unsigned short v = _inw(port);
 	delay();
 	return (v);
 }
 
 unsigned long _inl_p(unsigned long port)
 {
-	unsigned long  v;
-
-	v = *(volatile unsigned long *)PORT2ADDR(port);
+	unsigned long v = _inl(port);
 	delay();
 	return (v);
 }
@@ -219,7 +183,6 @@
 		*(volatile unsigned short *)PORT2ADDR_USB(port) = w;
 	else
 #endif
-
 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
 	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
 		pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
@@ -240,43 +203,19 @@
 
 void _outb_p(unsigned char b, unsigned long port)
 {
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		_ne_outb(b, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
-	} else
-#endif
-		*(volatile unsigned char *)PORT2ADDR(port) = b;
-
+	_outb(b, port);
 	delay();
 }
 
 void _outw_p(unsigned short w, unsigned long port)
 {
-	if (port >= LAN_IOSTART && port < LAN_IOEND)
-		_ne_outw(w, PORT2ADDR_NE(port));
-	else
-#if defined(CONFIG_USB)
-	if(port >= 0x340 && port < 0x3a0)
-		*(volatile unsigned short *)PORT2ADDR_USB(port) = w;
-	else
-#endif
-
-#if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
-	if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
-		pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
-	} else
-#endif
-		*(volatile unsigned short *)PORT2ADDR(port) = w;
-
+	_outw(w, port);
 	delay();
 }
 
 void _outl_p(unsigned long l, unsigned long port)
 {
-	*(volatile unsigned long *)PORT2ADDR(port) = l;
+	_outl(l, port);
 	delay();
 }
 
diff --git a/arch/m32r/kernel/io_usrv.c b/arch/m32r/kernel/io_usrv.c
index 27928a0..9eb161d 100644
--- a/arch/m32r/kernel/io_usrv.c
+++ b/arch/m32r/kernel/io_usrv.c
@@ -3,8 +3,8 @@
  *
  *  Typical I/O routines for uServer board.
  *
- *  Copyright (c) 2001 - 2003  Hiroyuki Kondo, Hirokazu Takata,
- *                             Hitoshi Yamamoto, Takeo Takahashi
+ *  Copyright (c) 2001-2005  Hiroyuki Kondo, Hirokazu Takata,
+ *                           Hitoshi Yamamoto, Takeo Takahashi
  *
  *  This file is subject to the terms and conditions of the GNU General
  *  Public License.  See the file "COPYING" in the main directory of this
@@ -39,7 +39,7 @@
 
 #define PORT2ADDR(port)	_port2addr(port)
 
-static __inline__ void *_port2addr(unsigned long port)
+static inline void *_port2addr(unsigned long port)
 {
 #if defined(CONFIG_SERIAL_8250) || defined(CONFIG_SERIAL_8250_MODULE)
 	if (port >= UART0_IOSTART && port <= UART0_IOEND)
@@ -50,7 +50,7 @@
 	return (void *)(port + NONCACHE_OFFSET);
 }
 
-static __inline__ void delay(void)
+static inline void delay(void)
 {
 	__asm__ __volatile__ ("push r0; \n\t pop r0;" : : :"memory");
 }
@@ -87,39 +87,22 @@
 
 unsigned char _inb_p(unsigned long port)
 {
-	unsigned char b;
-
-	if (port >= CFC_IOSTART && port <= CFC_IOEND) {
-		pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
-		return b;
-	} else {
-		b = *(volatile unsigned char *)PORT2ADDR(port);
-		delay();
-		return b;
-	}
+	unsigned char v = _inb(port);
+	delay();
+	return v;
 }
 
 unsigned short _inw_p(unsigned long port)
 {
-	unsigned short w;
-
-	if (port >= CFC_IOSTART && port <= CFC_IOEND) {
-		pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
-		return w;
-	} else {
-		w = *(volatile unsigned short *)PORT2ADDR(port);
-		delay();
-		return w;
-	}
+	unsigned short v = _inw(port);
+	delay();
+	return v;
 }
 
 unsigned long _inl_p(unsigned long port)
 {
-	unsigned long v;
-
-	v = *(volatile unsigned long *)PORT2ADDR(port);
+	unsigned long v = _inl(port);
 	delay();
-
 	return v;
 }
 
@@ -149,25 +132,19 @@
 
 void _outb_p(unsigned char b, unsigned long port)
 {
-	if (port >= CFC_IOSTART && port <= CFC_IOEND)
-		pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
-	else
-		*(volatile unsigned char *)PORT2ADDR(port) = b;
+	_outb(b, port);
 	delay();
 }
 
 void _outw_p(unsigned short w, unsigned long port)
 {
-	if (port >= CFC_IOSTART && port <= CFC_IOEND)
-		pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
-	else
-		*(volatile unsigned short *)PORT2ADDR(port) = w;
+	_outw(w, port);
 	delay();
 }
 
 void _outl_p(unsigned long l, unsigned long port)
 {
-	*(volatile unsigned long *)PORT2ADDR(port) = l;
+	_outl(l, port);
 	delay();
 }
 
diff --git a/arch/m32r/kernel/setup.c b/arch/m32r/kernel/setup.c
index 4826cd6..ec56747 100644
--- a/arch/m32r/kernel/setup.c
+++ b/arch/m32r/kernel/setup.c
@@ -330,6 +330,8 @@
 	seq_printf(m, "Machine\t\t: Mappi Evaluation board\n");
 #elif CONFIG_PLAT_MAPPI2
 	seq_printf(m, "Machine\t\t: Mappi-II Evaluation board\n");
+#elif CONFIG_PLAT_MAPPI3
+	seq_printf(m, "Machine\t\t: Mappi-III Evaluation board\n");
 #elif  CONFIG_PLAT_M32700UT
 	seq_printf(m, "Machine\t\t: M32700UT Evaluation board\n");
 #elif  CONFIG_PLAT_OPSPUT
diff --git a/arch/m32r/kernel/setup_m32700ut.c b/arch/m32r/kernel/setup_m32700ut.c
index 488aa87..b014e2c 100644
--- a/arch/m32r/kernel/setup_m32700ut.c
+++ b/arch/m32r/kernel/setup_m32700ut.c
@@ -78,13 +78,13 @@
 
 static struct hw_interrupt_type m32700ut_irq_type =
 {
-	"M32700UT-IRQ",
-	startup_m32700ut_irq,
-	shutdown_m32700ut_irq,
-	enable_m32700ut_irq,
-	disable_m32700ut_irq,
-	mask_and_ack_m32700ut,
-	end_m32700ut_irq
+	.typename = "M32700UT-IRQ",
+	.startup = startup_m32700ut_irq,
+	.shutdown = shutdown_m32700ut_irq,
+	.enable = enable_m32700ut_irq,
+	.disable = disable_m32700ut_irq,
+	.ack = mask_and_ack_m32700ut,
+	.end = end_m32700ut_irq
 };
 
 /*
@@ -155,13 +155,13 @@
 
 static struct hw_interrupt_type m32700ut_pld_irq_type =
 {
-	"M32700UT-PLD-IRQ",
-	startup_m32700ut_pld_irq,
-	shutdown_m32700ut_pld_irq,
-	enable_m32700ut_pld_irq,
-	disable_m32700ut_pld_irq,
-	mask_and_ack_m32700ut_pld,
-	end_m32700ut_pld_irq
+	.typename = "M32700UT-PLD-IRQ",
+	.startup = startup_m32700ut_pld_irq,
+	.shutdown = shutdown_m32700ut_pld_irq,
+	.enable = enable_m32700ut_pld_irq,
+	.disable = disable_m32700ut_pld_irq,
+	.ack = mask_and_ack_m32700ut_pld,
+	.end = end_m32700ut_pld_irq
 };
 
 /*
@@ -224,13 +224,13 @@
 
 static struct hw_interrupt_type m32700ut_lanpld_irq_type =
 {
-	"M32700UT-PLD-LAN-IRQ",
-	startup_m32700ut_lanpld_irq,
-	shutdown_m32700ut_lanpld_irq,
-	enable_m32700ut_lanpld_irq,
-	disable_m32700ut_lanpld_irq,
-	mask_and_ack_m32700ut_lanpld,
-	end_m32700ut_lanpld_irq
+	.typename = "M32700UT-PLD-LAN-IRQ",
+	.startup = startup_m32700ut_lanpld_irq,
+	.shutdown = shutdown_m32700ut_lanpld_irq,
+	.enable = enable_m32700ut_lanpld_irq,
+	.disable = disable_m32700ut_lanpld_irq,
+	.ack = mask_and_ack_m32700ut_lanpld,
+	.end = end_m32700ut_lanpld_irq
 };
 
 /*
@@ -293,13 +293,13 @@
 
 static struct hw_interrupt_type m32700ut_lcdpld_irq_type =
 {
-	"M32700UT-PLD-LCD-IRQ",
-	startup_m32700ut_lcdpld_irq,
-	shutdown_m32700ut_lcdpld_irq,
-	enable_m32700ut_lcdpld_irq,
-	disable_m32700ut_lcdpld_irq,
-	mask_and_ack_m32700ut_lcdpld,
-	end_m32700ut_lcdpld_irq
+	.typename = "M32700UT-PLD-LCD-IRQ",
+	.startup = startup_m32700ut_lcdpld_irq,
+	.shutdown = shutdown_m32700ut_lcdpld_irq,
+	.enable = enable_m32700ut_lcdpld_irq,
+	.disable = disable_m32700ut_lcdpld_irq,
+	.ack = mask_and_ack_m32700ut_lcdpld,
+	.end = end_m32700ut_lcdpld_irq
 };
 
 void __init init_IRQ(void)
diff --git a/arch/m32r/kernel/setup_mappi.c b/arch/m32r/kernel/setup_mappi.c
index 1e74110..aaf8e56 100644
--- a/arch/m32r/kernel/setup_mappi.c
+++ b/arch/m32r/kernel/setup_mappi.c
@@ -70,13 +70,13 @@
 
 static struct hw_interrupt_type mappi_irq_type =
 {
-	"MAPPI-IRQ",
-	startup_mappi_irq,
-	shutdown_mappi_irq,
-	enable_mappi_irq,
-	disable_mappi_irq,
-	mask_and_ack_mappi,
-	end_mappi_irq
+	.typename = "MAPPI-IRQ",
+	.startup = startup_mappi_irq,
+	.shutdown = shutdown_mappi_irq,
+	.enable = enable_mappi_irq,
+	.disable = disable_mappi_irq,
+	.ack = mask_and_ack_mappi,
+	.end = end_mappi_irq
 };
 
 void __init init_IRQ(void)
diff --git a/arch/m32r/kernel/setup_mappi2.c b/arch/m32r/kernel/setup_mappi2.c
index 1904d46..38d5e9a 100644
--- a/arch/m32r/kernel/setup_mappi2.c
+++ b/arch/m32r/kernel/setup_mappi2.c
@@ -1,5 +1,5 @@
 /*
- *  linux/arch/m32r/kernel/setup_mappi.c
+ *  linux/arch/m32r/kernel/setup_mappi2.c
  *
  *  Setup routines for Renesas MAPPI-II(M3A-ZA36) Board
  *
@@ -79,13 +79,13 @@
 
 static struct hw_interrupt_type mappi2_irq_type =
 {
-	"MAPPI2-IRQ",
-	startup_mappi2_irq,
-	shutdown_mappi2_irq,
-	enable_mappi2_irq,
-	disable_mappi2_irq,
-	mask_and_ack_mappi2,
-	end_mappi2_irq
+	.typename = "MAPPI2-IRQ",
+	.startup = startup_mappi2_irq,
+	.shutdown = shutdown_mappi2_irq,
+	.enable = enable_mappi2_irq,
+	.disable = disable_mappi2_irq,
+	.ack = mask_and_ack_mappi2,
+	.end = end_mappi2_irq
 };
 
 void __init init_IRQ(void)
@@ -156,7 +156,6 @@
 	irq_desc[PLD_IRQ_CFIREQ].handler = &mappi2_irq_type;
 	irq_desc[PLD_IRQ_CFIREQ].action = 0;
 	irq_desc[PLD_IRQ_CFIREQ].depth = 1;	/* disable nested irq */
-//	icu_data[PLD_IRQ_CFIREQ].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD00;
 	icu_data[PLD_IRQ_CFIREQ].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD01;
 	disable_mappi2_irq(PLD_IRQ_CFIREQ);
 
@@ -167,7 +166,6 @@
 	irq_desc[PLD_IRQ_CFC_INSERT].action = 0;
 	irq_desc[PLD_IRQ_CFC_INSERT].depth = 1;	/* disable nested irq */
 	icu_data[PLD_IRQ_CFC_INSERT].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD00;
-//	icu_data[PLD_IRQ_CFC_INSERT].icucr = 0;
 	disable_mappi2_irq(PLD_IRQ_CFC_INSERT);
 
 	/* ICUCR42: CFC Eject */
@@ -176,9 +174,7 @@
 	irq_desc[PLD_IRQ_CFC_EJECT].action = 0;
 	irq_desc[PLD_IRQ_CFC_EJECT].depth = 1;	/* disable nested irq */
 	icu_data[PLD_IRQ_CFC_EJECT].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD10;
-//	icu_data[PLD_IRQ_CFC_EJECT].icucr = 0;
 	disable_mappi2_irq(PLD_IRQ_CFC_EJECT);
-
 #endif /* CONFIG_MAPPI2_CFC */
 }
 
diff --git a/arch/m32r/kernel/setup_mappi3.c b/arch/m32r/kernel/setup_mappi3.c
new file mode 100644
index 0000000..3d60a85
--- /dev/null
+++ b/arch/m32r/kernel/setup_mappi3.c
@@ -0,0 +1,208 @@
+/*
+ *  linux/arch/m32r/kernel/setup_mappi3.c
+ *
+ *  Setup routines for Renesas MAPPI-III(M3A-2170) Board
+ *
+ *  Copyright (c) 2001-2005   Hiroyuki Kondo, Hirokazu Takata,
+ *                            Hitoshi Yamamoto, Mamoru Sakugawa
+ */
+
+#include <linux/config.h>
+#include <linux/irq.h>
+#include <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/device.h>
+
+#include <asm/system.h>
+#include <asm/m32r.h>
+#include <asm/io.h>
+
+#define irq2port(x) (M32R_ICU_CR1_PORTL + ((x - 1) * sizeof(unsigned long)))
+
+#ifndef CONFIG_SMP
+typedef struct {
+	unsigned long icucr;  /* ICU Control Register */
+} icu_data_t;
+#endif /* CONFIG_SMP */
+
+icu_data_t icu_data[NR_IRQS];
+
+static void disable_mappi3_irq(unsigned int irq)
+{
+	unsigned long port, data;
+
+	if ((irq == 0) ||(irq >= NR_IRQS))  {
+		printk("bad irq 0x%08x\n", irq);
+		return;
+	}
+	port = irq2port(irq);
+	data = icu_data[irq].icucr|M32R_ICUCR_ILEVEL7;
+	outl(data, port);
+}
+
+static void enable_mappi3_irq(unsigned int irq)
+{
+	unsigned long port, data;
+
+	if ((irq == 0) ||(irq >= NR_IRQS))  {
+		printk("bad irq 0x%08x\n", irq);
+		return;
+	}
+	port = irq2port(irq);
+	data = icu_data[irq].icucr|M32R_ICUCR_IEN|M32R_ICUCR_ILEVEL6;
+	outl(data, port);
+}
+
+static void mask_and_ack_mappi3(unsigned int irq)
+{
+	disable_mappi3_irq(irq);
+}
+
+static void end_mappi3_irq(unsigned int irq)
+{
+	enable_mappi3_irq(irq);
+}
+
+static unsigned int startup_mappi3_irq(unsigned int irq)
+{
+	enable_mappi3_irq(irq);
+	return (0);
+}
+
+static void shutdown_mappi3_irq(unsigned int irq)
+{
+	unsigned long port;
+
+	port = irq2port(irq);
+	outl(M32R_ICUCR_ILEVEL7, port);
+}
+
+static struct hw_interrupt_type mappi3_irq_type =
+{
+	.typename = "MAPPI3-IRQ",
+	.startup = startup_mappi3_irq,
+	.shutdown = shutdown_mappi3_irq,
+	.enable = enable_mappi3_irq,
+	.disable = disable_mappi3_irq,
+	.ack = mask_and_ack_mappi3,
+	.end = end_mappi3_irq
+};
+
+void __init init_IRQ(void)
+{
+#if defined(CONFIG_SMC91X)
+	/* INT0 : LAN controller (SMC91111) */
+	irq_desc[M32R_IRQ_INT0].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_INT0].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_INT0].action = 0;
+	irq_desc[M32R_IRQ_INT0].depth = 1;
+	icu_data[M32R_IRQ_INT0].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD10;
+	disable_mappi3_irq(M32R_IRQ_INT0);
+#endif  /* CONFIG_SMC91X */
+
+	/* MFT2 : system timer */
+	irq_desc[M32R_IRQ_MFT2].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_MFT2].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_MFT2].action = 0;
+	irq_desc[M32R_IRQ_MFT2].depth = 1;
+	icu_data[M32R_IRQ_MFT2].icucr = M32R_ICUCR_IEN;
+	disable_mappi3_irq(M32R_IRQ_MFT2);
+
+#ifdef CONFIG_SERIAL_M32R_SIO
+	/* SIO0_R : uart receive data */
+	irq_desc[M32R_IRQ_SIO0_R].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_SIO0_R].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_SIO0_R].action = 0;
+	irq_desc[M32R_IRQ_SIO0_R].depth = 1;
+	icu_data[M32R_IRQ_SIO0_R].icucr = 0;
+	disable_mappi3_irq(M32R_IRQ_SIO0_R);
+
+	/* SIO0_S : uart send data */
+	irq_desc[M32R_IRQ_SIO0_S].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_SIO0_S].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_SIO0_S].action = 0;
+	irq_desc[M32R_IRQ_SIO0_S].depth = 1;
+	icu_data[M32R_IRQ_SIO0_S].icucr = 0;
+	disable_mappi3_irq(M32R_IRQ_SIO0_S);
+	/* SIO1_R : uart receive data */
+	irq_desc[M32R_IRQ_SIO1_R].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_SIO1_R].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_SIO1_R].action = 0;
+	irq_desc[M32R_IRQ_SIO1_R].depth = 1;
+	icu_data[M32R_IRQ_SIO1_R].icucr = 0;
+	disable_mappi3_irq(M32R_IRQ_SIO1_R);
+
+	/* SIO1_S : uart send data */
+	irq_desc[M32R_IRQ_SIO1_S].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_SIO1_S].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_SIO1_S].action = 0;
+	irq_desc[M32R_IRQ_SIO1_S].depth = 1;
+	icu_data[M32R_IRQ_SIO1_S].icucr = 0;
+	disable_mappi3_irq(M32R_IRQ_SIO1_S);
+#endif  /* CONFIG_M32R_USE_DBG_CONSOLE */
+
+#if defined(CONFIG_USB)
+	/* INT1 : USB Host controller interrupt */
+	irq_desc[M32R_IRQ_INT1].status = IRQ_DISABLED;
+	irq_desc[M32R_IRQ_INT1].handler = &mappi3_irq_type;
+	irq_desc[M32R_IRQ_INT1].action = 0;
+	irq_desc[M32R_IRQ_INT1].depth = 1;
+	icu_data[M32R_IRQ_INT1].icucr = M32R_ICUCR_ISMOD01;
+	disable_mappi3_irq(M32R_IRQ_INT1);
+#endif /* CONFIG_USB */
+
+	/* ICUCR40: CFC IREQ */
+	irq_desc[PLD_IRQ_CFIREQ].status = IRQ_DISABLED;
+	irq_desc[PLD_IRQ_CFIREQ].handler = &mappi3_irq_type;
+	irq_desc[PLD_IRQ_CFIREQ].action = 0;
+	irq_desc[PLD_IRQ_CFIREQ].depth = 1;	/* disable nested irq */
+	icu_data[PLD_IRQ_CFIREQ].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD01;
+	disable_mappi3_irq(PLD_IRQ_CFIREQ);
+
+#if defined(CONFIG_M32R_CFC)
+	/* ICUCR41: CFC Insert */
+	irq_desc[PLD_IRQ_CFC_INSERT].status = IRQ_DISABLED;
+	irq_desc[PLD_IRQ_CFC_INSERT].handler = &mappi3_irq_type;
+	irq_desc[PLD_IRQ_CFC_INSERT].action = 0;
+	irq_desc[PLD_IRQ_CFC_INSERT].depth = 1;	/* disable nested irq */
+	icu_data[PLD_IRQ_CFC_INSERT].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD00;
+	disable_mappi3_irq(PLD_IRQ_CFC_INSERT);
+
+	/* ICUCR42: CFC Eject */
+	irq_desc[PLD_IRQ_CFC_EJECT].status = IRQ_DISABLED;
+	irq_desc[PLD_IRQ_CFC_EJECT].handler = &mappi3_irq_type;
+	irq_desc[PLD_IRQ_CFC_EJECT].action = 0;
+	irq_desc[PLD_IRQ_CFC_EJECT].depth = 1;	/* disable nested irq */
+	icu_data[PLD_IRQ_CFC_EJECT].icucr = M32R_ICUCR_IEN|M32R_ICUCR_ISMOD10;
+	disable_mappi3_irq(PLD_IRQ_CFC_EJECT);
+#endif /* CONFIG_M32R_CFC */
+}
+
+#define LAN_IOSTART     0x300
+#define LAN_IOEND       0x320
+static struct resource smc91x_resources[] = {
+	[0] = {
+		.start  = (LAN_IOSTART),
+		.end    = (LAN_IOEND),
+		.flags  = IORESOURCE_MEM,
+	},
+	[1] = {
+		.start  = M32R_IRQ_INT0,
+		.end    = M32R_IRQ_INT0,
+		.flags  = IORESOURCE_IRQ,
+	}
+};
+
+static struct platform_device smc91x_device = {
+	.name		= "smc91x",
+	.id		= 0,
+	.num_resources  = ARRAY_SIZE(smc91x_resources),
+	.resource       = smc91x_resources,
+};
+
+static int __init platform_init(void)
+{
+	platform_device_register(&smc91x_device);
+	return 0;
+}
+arch_initcall(platform_init);
diff --git a/arch/m32r/kernel/setup_oaks32r.c b/arch/m32r/kernel/setup_oaks32r.c
index b048345..d656640 100644
--- a/arch/m32r/kernel/setup_oaks32r.c
+++ b/arch/m32r/kernel/setup_oaks32r.c
@@ -70,13 +70,13 @@
 
 static struct hw_interrupt_type oaks32r_irq_type =
 {
-	"OAKS32R-IRQ",
-	startup_oaks32r_irq,
-	shutdown_oaks32r_irq,
-	enable_oaks32r_irq,
-	disable_oaks32r_irq,
-	mask_and_ack_mappi,
-	end_oaks32r_irq
+	.typename = "OAKS32R-IRQ",
+	.startup = startup_oaks32r_irq,
+	.shutdown = shutdown_oaks32r_irq,
+	.enable = enable_oaks32r_irq,
+	.disable = disable_oaks32r_irq,
+	.ack = mask_and_ack_mappi,
+	.end = end_oaks32r_irq
 };
 
 void __init init_IRQ(void)
diff --git a/arch/m32r/kernel/setup_opsput.c b/arch/m32r/kernel/setup_opsput.c
index 84315e3..86f4cf2 100644
--- a/arch/m32r/kernel/setup_opsput.c
+++ b/arch/m32r/kernel/setup_opsput.c
@@ -79,13 +79,13 @@
 
 static struct hw_interrupt_type opsput_irq_type =
 {
-	"OPSPUT-IRQ",
-	startup_opsput_irq,
-	shutdown_opsput_irq,
-	enable_opsput_irq,
-	disable_opsput_irq,
-	mask_and_ack_opsput,
-	end_opsput_irq
+	.typename = "OPSPUT-IRQ",
+	.startup = startup_opsput_irq,
+	.shutdown = shutdown_opsput_irq,
+	.enable = enable_opsput_irq,
+	.disable = disable_opsput_irq,
+	.ack = mask_and_ack_opsput,
+	.end = end_opsput_irq
 };
 
 /*
@@ -156,13 +156,13 @@
 
 static struct hw_interrupt_type opsput_pld_irq_type =
 {
-	"OPSPUT-PLD-IRQ",
-	startup_opsput_pld_irq,
-	shutdown_opsput_pld_irq,
-	enable_opsput_pld_irq,
-	disable_opsput_pld_irq,
-	mask_and_ack_opsput_pld,
-	end_opsput_pld_irq
+	.typename = "OPSPUT-PLD-IRQ",
+	.startup = startup_opsput_pld_irq,
+	.shutdown = shutdown_opsput_pld_irq,
+	.enable = enable_opsput_pld_irq,
+	.disable = disable_opsput_pld_irq,
+	.ack = mask_and_ack_opsput_pld,
+	.end = end_opsput_pld_irq
 };
 
 /*
diff --git a/arch/m32r/kernel/setup_usrv.c b/arch/m32r/kernel/setup_usrv.c
index fe417be..634741b 100644
--- a/arch/m32r/kernel/setup_usrv.c
+++ b/arch/m32r/kernel/setup_usrv.c
@@ -70,13 +70,13 @@
 
 static struct hw_interrupt_type mappi_irq_type =
 {
-	"M32700-IRQ",
-	startup_mappi_irq,
-	shutdown_mappi_irq,
-	enable_mappi_irq,
-	disable_mappi_irq,
-	mask_and_ack_mappi,
-	end_mappi_irq
+	.typename = "M32700-IRQ",
+	.startup = startup_mappi_irq,
+	.shutdown = shutdown_mappi_irq,
+	.enable = enable_mappi_irq,
+	.disable = disable_mappi_irq,
+	.ack = mask_and_ack_mappi,
+	.end = end_mappi_irq
 };
 
 /*
@@ -143,13 +143,13 @@
 
 static struct hw_interrupt_type m32700ut_pld_irq_type =
 {
-	"USRV-PLD-IRQ",
-	startup_m32700ut_pld_irq,
-	shutdown_m32700ut_pld_irq,
-	enable_m32700ut_pld_irq,
-	disable_m32700ut_pld_irq,
-	mask_and_ack_m32700ut_pld,
-	end_m32700ut_pld_irq
+	.typename = "USRV-PLD-IRQ",
+	.startup = startup_m32700ut_pld_irq,
+	.shutdown = shutdown_m32700ut_pld_irq,
+	.enable = enable_m32700ut_pld_irq,
+	.disable = disable_m32700ut_pld_irq,
+	.ack = mask_and_ack_m32700ut_pld,
+	.end = end_m32700ut_pld_irq
 };
 
 void __init init_IRQ(void)
diff --git a/arch/m32r/m32700ut/defconfig.m32700ut.smp b/arch/m32r/m32700ut/defconfig.m32700ut.smp
index 1c00218..3e607d9 100644
--- a/arch/m32r/m32700ut/defconfig.m32700ut.smp
+++ b/arch/m32r/m32700ut/defconfig.m32700ut.smp
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:10:50 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:20:58 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -15,6 +15,7 @@
 CONFIG_EXPERIMENTAL=y
 CONFIG_CLEAN_COMPILE=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -27,13 +28,16 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=15
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 # CONFIG_IKCONFIG_PROC is not set
+# CONFIG_CPUSETS is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -43,6 +47,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -65,6 +70,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 CONFIG_CHIP_M32700=y
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -271,7 +277,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -396,18 +401,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -417,6 +410,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 CONFIG_VT=y
@@ -468,6 +472,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -511,8 +519,14 @@
 # Graphics support
 #
 CONFIG_FB=y
+# CONFIG_FB_CFB_FILLRECT is not set
+# CONFIG_FB_CFB_COPYAREA is not set
+# CONFIG_FB_CFB_IMAGEBLIT is not set
+# CONFIG_FB_SOFT_CURSOR is not set
+# CONFIG_FB_MACMODES is not set
 # CONFIG_FB_MODE_HELPERS is not set
 # CONFIG_FB_TILEBLITTING is not set
+# CONFIG_FB_S1D13XXX is not set
 # CONFIG_FB_VIRTUAL is not set
 
 #
@@ -546,10 +560,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -722,8 +732,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=15
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/m32700ut/defconfig.m32700ut.up b/arch/m32r/m32700ut/defconfig.m32700ut.up
index 805357f..2d3e7cd 100644
--- a/arch/m32r/m32700ut/defconfig.m32700ut.up
+++ b/arch/m32r/m32700ut/defconfig.m32700ut.up
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:10:54 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:21:34 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -16,6 +16,7 @@
 CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -28,13 +29,15 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 # CONFIG_IKCONFIG_PROC is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -44,6 +47,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -65,6 +69,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 CONFIG_CHIP_M32700=y
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -268,7 +273,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -393,18 +397,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -414,6 +406,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 CONFIG_VT=y
@@ -465,6 +468,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -508,8 +515,14 @@
 # Graphics support
 #
 CONFIG_FB=y
+# CONFIG_FB_CFB_FILLRECT is not set
+# CONFIG_FB_CFB_COPYAREA is not set
+# CONFIG_FB_CFB_IMAGEBLIT is not set
+# CONFIG_FB_SOFT_CURSOR is not set
+# CONFIG_FB_MACMODES is not set
 # CONFIG_FB_MODE_HELPERS is not set
 # CONFIG_FB_TILEBLITTING is not set
+# CONFIG_FB_S1D13XXX is not set
 # CONFIG_FB_VIRTUAL is not set
 
 #
@@ -543,10 +556,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -719,8 +728,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/mappi/defconfig.nommu b/arch/m32r/mappi/defconfig.nommu
index 714aa6e..a8425fb 100644
--- a/arch/m32r/mappi/defconfig.nommu
+++ b/arch/m32r/mappi/defconfig.nommu
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:10:57 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:21:46 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -16,6 +16,7 @@
 CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -26,13 +27,15 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 # CONFIG_IKCONFIG_PROC is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -41,6 +44,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_TINY_SHMEM=y
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -62,6 +66,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 CONFIG_CHIP_M32700=y
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -202,7 +207,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -325,18 +329,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -346,6 +338,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 # CONFIG_VT is not set
@@ -394,6 +397,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -434,10 +441,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -595,8 +598,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/mappi/defconfig.smp b/arch/m32r/mappi/defconfig.smp
index 956a8e2..1a7f3cd 100644
--- a/arch/m32r/mappi/defconfig.smp
+++ b/arch/m32r/mappi/defconfig.smp
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:11:02 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:21:52 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -17,6 +17,7 @@
 CONFIG_BROKEN=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -28,13 +29,16 @@
 # CONFIG_BSD_PROCESS_ACCT is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=15
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 CONFIG_IKCONFIG_PROC=y
+# CONFIG_CPUSETS is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -44,6 +48,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -66,6 +71,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 CONFIG_CHIP_M32700=y
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -139,8 +145,8 @@
 #
 CONFIG_MTD=y
 # CONFIG_MTD_DEBUG is not set
-CONFIG_MTD_PARTITIONS=y
 # CONFIG_MTD_CONCAT is not set
+CONFIG_MTD_PARTITIONS=y
 CONFIG_MTD_REDBOOT_PARTS=y
 CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1
 # CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
@@ -294,7 +300,6 @@
 # Networking options
 #
 # CONFIG_PACKET is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -420,18 +425,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-# CONFIG_SERIO_SERPORT is not set
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -441,6 +434,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+# CONFIG_SERIO_SERPORT is not set
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 # CONFIG_VT is not set
@@ -489,6 +493,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -529,10 +537,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -708,8 +712,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=15
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/mappi/defconfig.up b/arch/m32r/mappi/defconfig.up
index c9253e9..38910fb 100644
--- a/arch/m32r/mappi/defconfig.up
+++ b/arch/m32r/mappi/defconfig.up
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:11:07 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:21:59 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -17,6 +17,7 @@
 CONFIG_BROKEN=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -28,13 +29,15 @@
 # CONFIG_BSD_PROCESS_ACCT is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 CONFIG_IKCONFIG_PROC=y
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -44,6 +47,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -65,6 +69,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 CONFIG_CHIP_M32700=y
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -135,8 +140,8 @@
 #
 CONFIG_MTD=y
 # CONFIG_MTD_DEBUG is not set
-CONFIG_MTD_PARTITIONS=y
 # CONFIG_MTD_CONCAT is not set
+CONFIG_MTD_PARTITIONS=y
 CONFIG_MTD_REDBOOT_PARTS=y
 CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1
 # CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
@@ -290,7 +295,6 @@
 # Networking options
 #
 # CONFIG_PACKET is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -416,18 +420,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-# CONFIG_SERIO_SERPORT is not set
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -437,6 +429,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+# CONFIG_SERIO_SERPORT is not set
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 # CONFIG_VT is not set
@@ -485,6 +488,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -525,10 +532,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -704,8 +707,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/mappi2/defconfig.vdec2 b/arch/m32r/mappi2/defconfig.vdec2
index c14791d..56f287b 100644
--- a/arch/m32r/mappi2/defconfig.vdec2
+++ b/arch/m32r/mappi2/defconfig.vdec2
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:11:10 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:22:02 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -16,6 +16,7 @@
 CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -28,13 +29,15 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 # CONFIG_IKCONFIG_PROC is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -44,6 +47,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -65,6 +69,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 # CONFIG_PLAT_OAKS32R is not set
 CONFIG_PLAT_MAPPI2=y
+# CONFIG_PLAT_MAPPI3 is not set
 # CONFIG_CHIP_M32700 is not set
 # CONFIG_CHIP_M32102 is not set
 CONFIG_CHIP_VDEC2=y
@@ -264,7 +269,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -389,18 +393,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -410,6 +402,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 CONFIG_VT=y
@@ -460,6 +463,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -521,10 +528,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -697,8 +700,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/mappi3/defconfig.smp b/arch/m32r/mappi3/defconfig.smp
new file mode 100644
index 0000000..2eebe75f
--- /dev/null
+++ b/arch/m32r/mappi3/defconfig.smp
@@ -0,0 +1,751 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.12-rc5
+# Tue May 31 17:55:34 2005
+#
+CONFIG_M32R=y
+# CONFIG_UID16 is not set
+CONFIG_GENERIC_ISA_DMA=y
+CONFIG_GENERIC_HARDIRQS=y
+CONFIG_GENERIC_IRQ_PROBE=y
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+# CONFIG_CLEAN_COMPILE is not set
+CONFIG_BROKEN=y
+CONFIG_BROKEN_ON_SMP=y
+CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+# CONFIG_POSIX_MQUEUE is not set
+# CONFIG_BSD_PROCESS_ACCT is not set
+CONFIG_SYSCTL=y
+# CONFIG_AUDIT is not set
+CONFIG_HOTPLUG=y
+CONFIG_KOBJECT_UEVENT=y
+CONFIG_IKCONFIG=y
+CONFIG_IKCONFIG_PROC=y
+# CONFIG_CPUSETS is not set
+CONFIG_EMBEDDED=y
+# CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
+# CONFIG_FUTEX is not set
+# CONFIG_EPOLL is not set
+# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
+CONFIG_SHMEM=y
+CONFIG_CC_ALIGN_FUNCTIONS=0
+CONFIG_CC_ALIGN_LABELS=0
+CONFIG_CC_ALIGN_LOOPS=0
+CONFIG_CC_ALIGN_JUMPS=0
+# CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+# CONFIG_MODVERSIONS is not set
+# CONFIG_MODULE_SRCVERSION_ALL is not set
+CONFIG_KMOD=y
+CONFIG_STOP_MACHINE=y
+
+#
+# Processor type and features
+#
+# CONFIG_PLAT_MAPPI is not set
+# CONFIG_PLAT_USRV is not set
+# CONFIG_PLAT_M32700UT is not set
+# CONFIG_PLAT_OPSPUT is not set
+# CONFIG_PLAT_OAKS32R is not set
+# CONFIG_PLAT_MAPPI2 is not set
+CONFIG_PLAT_MAPPI3=y
+CONFIG_CHIP_M32700=y
+# CONFIG_CHIP_M32102 is not set
+# CONFIG_CHIP_VDEC2 is not set
+# CONFIG_CHIP_OPSP is not set
+CONFIG_MMU=y
+CONFIG_TLB_ENTRIES=32
+CONFIG_ISA_M32R2=y
+CONFIG_ISA_DSP_LEVEL2=y
+CONFIG_ISA_DUAL_ISSUE=y
+CONFIG_BUS_CLOCK=10000000
+CONFIG_TIMER_DIVIDE=128
+# CONFIG_CPU_LITTLE_ENDIAN is not set
+CONFIG_MEMORY_START=0x08000000
+CONFIG_MEMORY_SIZE=0x08000000
+CONFIG_NOHIGHMEM=y
+CONFIG_DISCONTIGMEM=y
+CONFIG_IRAM_START=0x00f00000
+CONFIG_IRAM_SIZE=0x00080000
+CONFIG_RWSEM_GENERIC_SPINLOCK=y
+# CONFIG_RWSEM_XCHGADD_ALGORITHM is not set
+CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_PREEMPT=y
+# CONFIG_HAVE_DEC_LOCK is not set
+CONFIG_SMP=y
+# CONFIG_CHIP_M32700_TS1 is not set
+CONFIG_NR_CPUS=2
+# CONFIG_NUMA is not set
+
+#
+# Bus options (PCI, PCMCIA, EISA, MCA, ISA)
+#
+# CONFIG_PCI is not set
+# CONFIG_ISA is not set
+
+#
+# PCCARD (PCMCIA/CardBus) support
+#
+CONFIG_PCCARD=y
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_PCMCIA=y
+
+#
+# PC-card bridges
+#
+# CONFIG_TCIC is not set
+# CONFIG_M32R_PCC is not set
+# CONFIG_M32R_CFC is not set
+
+#
+# PCI Hotplug Support
+#
+
+#
+# Executable file formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_MISC is not set
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+CONFIG_FW_LOADER=y
+
+#
+# Memory Technology Devices (MTD)
+#
+CONFIG_MTD=y
+# CONFIG_MTD_DEBUG is not set
+# CONFIG_MTD_CONCAT is not set
+CONFIG_MTD_PARTITIONS=y
+CONFIG_MTD_REDBOOT_PARTS=y
+CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1
+# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
+# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
+# CONFIG_MTD_CMDLINE_PARTS is not set
+
+#
+# User Modules And Translation Layers
+#
+CONFIG_MTD_CHAR=y
+CONFIG_MTD_BLOCK=y
+# CONFIG_FTL is not set
+# CONFIG_NFTL is not set
+# CONFIG_INFTL is not set
+
+#
+# RAM/ROM/Flash chip drivers
+#
+# CONFIG_MTD_CFI is not set
+# CONFIG_MTD_JEDECPROBE is not set
+CONFIG_MTD_MAP_BANK_WIDTH_1=y
+CONFIG_MTD_MAP_BANK_WIDTH_2=y
+CONFIG_MTD_MAP_BANK_WIDTH_4=y
+# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set
+# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set
+# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set
+CONFIG_MTD_CFI_I1=y
+CONFIG_MTD_CFI_I2=y
+# CONFIG_MTD_CFI_I4 is not set
+# CONFIG_MTD_CFI_I8 is not set
+# CONFIG_MTD_RAM is not set
+# CONFIG_MTD_ROM is not set
+# CONFIG_MTD_ABSENT is not set
+# CONFIG_MTD_OBSOLETE_CHIPS is not set
+
+#
+# Mapping drivers for chip access
+#
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+
+#
+# Self-contained MTD device drivers
+#
+# CONFIG_MTD_SLRAM is not set
+# CONFIG_MTD_PHRAM is not set
+# CONFIG_MTD_MTDRAM is not set
+# CONFIG_MTD_BLKMTD is not set
+# CONFIG_MTD_BLOCK2MTD is not set
+
+#
+# Disk-On-Chip Device Drivers
+#
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+
+#
+# NAND Flash Device Drivers
+#
+# CONFIG_MTD_NAND is not set
+
+#
+# Parallel port support
+#
+# CONFIG_PARPORT is not set
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_BLK_DEV_FD is not set
+# CONFIG_BLK_DEV_COW_COMMON is not set
+CONFIG_BLK_DEV_LOOP=y
+# CONFIG_BLK_DEV_CRYPTOLOOP is not set
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_COUNT=16
+CONFIG_BLK_DEV_RAM_SIZE=4096
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_INITRAMFS_SOURCE=""
+# CONFIG_CDROM_PKTCDVD is not set
+
+#
+# IO Schedulers
+#
+CONFIG_IOSCHED_NOOP=y
+# CONFIG_IOSCHED_AS is not set
+CONFIG_IOSCHED_DEADLINE=y
+CONFIG_IOSCHED_CFQ=y
+# CONFIG_ATA_OVER_ETH is not set
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_IDE_SATA is not set
+CONFIG_BLK_DEV_IDEDISK=y
+# CONFIG_IDEDISK_MULTI_MODE is not set
+CONFIG_BLK_DEV_IDECS=y
+CONFIG_BLK_DEV_IDECD=m
+# CONFIG_BLK_DEV_IDETAPE is not set
+# CONFIG_BLK_DEV_IDEFLOPPY is not set
+# CONFIG_IDE_TASK_IOCTL is not set
+
+#
+# IDE chipset support/bugfixes
+#
+CONFIG_IDE_GENERIC=y
+# CONFIG_IDE_ARM is not set
+# CONFIG_BLK_DEV_IDEDMA is not set
+# CONFIG_IDEDMA_AUTO is not set
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+# CONFIG_SCSI is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+# CONFIG_MD is not set
+
+#
+# Fusion MPT device support
+#
+
+#
+# IEEE 1394 (FireWire) support
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# I2O device support
+#
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+# CONFIG_PACKET is not set
+CONFIG_UNIX=y
+# CONFIG_NET_KEY is not set
+CONFIG_INET=y
+# CONFIG_IP_MULTICAST is not set
+# CONFIG_IP_ADVANCED_ROUTER is not set
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+# CONFIG_IP_PNP_BOOTP is not set
+# CONFIG_IP_PNP_RARP is not set
+# CONFIG_NET_IPIP is not set
+# CONFIG_NET_IPGRE is not set
+# CONFIG_ARPD is not set
+# CONFIG_SYN_COOKIES is not set
+# CONFIG_INET_AH is not set
+# CONFIG_INET_ESP is not set
+# CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_TUNNEL is not set
+CONFIG_IP_TCPDIAG=y
+# CONFIG_IP_TCPDIAG_IPV6 is not set
+# CONFIG_IPV6 is not set
+# CONFIG_NETFILTER is not set
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_SCTP is not set
+# CONFIG_ATM is not set
+# CONFIG_BRIDGE is not set
+# CONFIG_VLAN_8021Q is not set
+# CONFIG_DECNET is not set
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+# CONFIG_NET_DIVERT is not set
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+# CONFIG_NET_SCHED is not set
+# CONFIG_NET_CLS_ROUTE is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+# CONFIG_NETPOLL is not set
+# CONFIG_NET_POLL_CONTROLLER is not set
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+# CONFIG_BT is not set
+CONFIG_NETDEVICES=y
+# CONFIG_DUMMY is not set
+# CONFIG_BONDING is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_TUN is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=y
+CONFIG_SMC91X=y
+# CONFIG_NE2000 is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+
+#
+# Ethernet (10000 Mbit)
+#
+
+#
+# Token Ring devices
+#
+
+#
+# Wireless LAN (non-hamradio)
+#
+# CONFIG_NET_RADIO is not set
+
+#
+# PCMCIA network device support
+#
+# CONFIG_NET_PCMCIA is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+# CONFIG_PPP is not set
+# CONFIG_SLIP is not set
+# CONFIG_SHAPER is not set
+# CONFIG_NETCONSOLE is not set
+
+#
+# ISDN subsystem
+#
+# CONFIG_ISDN is not set
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+CONFIG_INPUT_MOUSEDEV_PSAUX=y
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+# CONFIG_INPUT_JOYDEV is not set
+# CONFIG_INPUT_TSDEV is not set
+# CONFIG_INPUT_EVDEV is not set
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input Device Drivers
+#
+# CONFIG_INPUT_KEYBOARD is not set
+# CONFIG_INPUT_MOUSE is not set
+# CONFIG_INPUT_JOYSTICK is not set
+# CONFIG_INPUT_TOUCHSCREEN is not set
+# CONFIG_INPUT_MISC is not set
+
+#
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+# CONFIG_SERIO_SERPORT is not set
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
+# Character devices
+#
+# CONFIG_VT is not set
+# CONFIG_SERIAL_NONSTANDARD is not set
+
+#
+# Serial drivers
+#
+# CONFIG_SERIAL_8250 is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_SERIAL_M32R_SIO=y
+CONFIG_SERIAL_M32R_SIO_CONSOLE=y
+# CONFIG_SERIAL_M32R_PLDSIO is not set
+CONFIG_UNIX98_PTYS=y
+CONFIG_LEGACY_PTYS=y
+CONFIG_LEGACY_PTY_COUNT=256
+
+#
+# IPMI
+#
+# CONFIG_IPMI_HANDLER is not set
+
+#
+# Watchdog Cards
+#
+# CONFIG_WATCHDOG is not set
+# CONFIG_RTC is not set
+# CONFIG_GEN_RTC is not set
+# CONFIG_DTLK is not set
+# CONFIG_R3964 is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+# CONFIG_DRM is not set
+
+#
+# PCMCIA character devices
+#
+# CONFIG_SYNCLINK_CS is not set
+# CONFIG_RAW_DRIVER is not set
+
+#
+# TPM devices
+#
+
+#
+# I2C support
+#
+# CONFIG_I2C is not set
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Misc devices
+#
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+
+#
+# Graphics support
+#
+# CONFIG_FB is not set
+
+#
+# Sound
+#
+# CONFIG_SOUND is not set
+
+#
+# USB support
+#
+# CONFIG_USB_ARCH_HAS_HCD is not set
+# CONFIG_USB_ARCH_HAS_OHCI is not set
+
+#
+# USB Gadget Support
+#
+# CONFIG_USB_GADGET is not set
+
+#
+# MMC/SD Card support
+#
+# CONFIG_MMC is not set
+
+#
+# InfiniBand support
+#
+# CONFIG_INFINIBAND is not set
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+# CONFIG_EXT2_FS_XATTR is not set
+CONFIG_EXT3_FS=y
+CONFIG_EXT3_FS_XATTR=y
+# CONFIG_EXT3_FS_POSIX_ACL is not set
+# CONFIG_EXT3_FS_SECURITY is not set
+CONFIG_JBD=y
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+
+#
+# XFS support
+#
+# CONFIG_XFS_FS is not set
+# CONFIG_MINIX_FS is not set
+CONFIG_ROMFS_FS=y
+# CONFIG_QUOTA is not set
+CONFIG_DNOTIFY=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_AUTOFS4_FS is not set
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+# CONFIG_JOLIET is not set
+# CONFIG_ZISOFS is not set
+# CONFIG_UDF_FS is not set
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+CONFIG_SYSFS=y
+CONFIG_DEVFS_FS=y
+CONFIG_DEVFS_MOUNT=y
+# CONFIG_DEVFS_DEBUG is not set
+# CONFIG_DEVPTS_FS_XATTR is not set
+CONFIG_TMPFS=y
+# CONFIG_TMPFS_XATTR is not set
+# CONFIG_HUGETLBFS is not set
+# CONFIG_HUGETLB_PAGE is not set
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_HFS_FS is not set
+# CONFIG_HFSPLUS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+CONFIG_JFFS_FS=y
+CONFIG_JFFS_FS_VERBOSE=0
+CONFIG_JFFS_PROC_FS=y
+CONFIG_JFFS2_FS=y
+CONFIG_JFFS2_FS_DEBUG=0
+# CONFIG_JFFS2_FS_NAND is not set
+# CONFIG_JFFS2_FS_NOR_ECC is not set
+# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
+CONFIG_JFFS2_ZLIB=y
+CONFIG_JFFS2_RTIME=y
+# CONFIG_JFFS2_RUBIN is not set
+# CONFIG_CRAMFS is not set
+# CONFIG_VXFS_FS is not set
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=y
+CONFIG_NFS_V3=y
+# CONFIG_NFS_V4 is not set
+# CONFIG_NFS_DIRECTIO is not set
+# CONFIG_NFSD is not set
+CONFIG_ROOT_NFS=y
+CONFIG_LOCKD=y
+CONFIG_LOCKD_V4=y
+CONFIG_SUNRPC=y
+# CONFIG_RPCSEC_GSS_KRB5 is not set
+# CONFIG_RPCSEC_GSS_SPKM3 is not set
+# CONFIG_SMB_FS is not set
+# CONFIG_CIFS is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+
+#
+# Partition Types
+#
+# CONFIG_PARTITION_ADVANCED is not set
+CONFIG_MSDOS_PARTITION=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS=y
+CONFIG_NLS_DEFAULT="iso8859-1"
+# CONFIG_NLS_CODEPAGE_437 is not set
+# CONFIG_NLS_CODEPAGE_737 is not set
+# CONFIG_NLS_CODEPAGE_775 is not set
+# CONFIG_NLS_CODEPAGE_850 is not set
+# CONFIG_NLS_CODEPAGE_852 is not set
+# CONFIG_NLS_CODEPAGE_855 is not set
+# CONFIG_NLS_CODEPAGE_857 is not set
+# CONFIG_NLS_CODEPAGE_860 is not set
+# CONFIG_NLS_CODEPAGE_861 is not set
+# CONFIG_NLS_CODEPAGE_862 is not set
+# CONFIG_NLS_CODEPAGE_863 is not set
+# CONFIG_NLS_CODEPAGE_864 is not set
+# CONFIG_NLS_CODEPAGE_865 is not set
+# CONFIG_NLS_CODEPAGE_866 is not set
+# CONFIG_NLS_CODEPAGE_869 is not set
+# CONFIG_NLS_CODEPAGE_936 is not set
+# CONFIG_NLS_CODEPAGE_950 is not set
+# CONFIG_NLS_CODEPAGE_932 is not set
+# CONFIG_NLS_CODEPAGE_949 is not set
+# CONFIG_NLS_CODEPAGE_874 is not set
+# CONFIG_NLS_ISO8859_8 is not set
+# CONFIG_NLS_CODEPAGE_1250 is not set
+# CONFIG_NLS_CODEPAGE_1251 is not set
+# CONFIG_NLS_ASCII is not set
+# CONFIG_NLS_ISO8859_1 is not set
+# CONFIG_NLS_ISO8859_2 is not set
+# CONFIG_NLS_ISO8859_3 is not set
+# CONFIG_NLS_ISO8859_4 is not set
+# CONFIG_NLS_ISO8859_5 is not set
+# CONFIG_NLS_ISO8859_6 is not set
+# CONFIG_NLS_ISO8859_7 is not set
+# CONFIG_NLS_ISO8859_9 is not set
+# CONFIG_NLS_ISO8859_13 is not set
+# CONFIG_NLS_ISO8859_14 is not set
+# CONFIG_NLS_ISO8859_15 is not set
+# CONFIG_NLS_KOI8_R is not set
+# CONFIG_NLS_KOI8_U is not set
+# CONFIG_NLS_UTF8 is not set
+
+#
+# Profiling support
+#
+# CONFIG_PROFILING is not set
+
+#
+# Kernel hacking
+#
+# CONFIG_PRINTK_TIME is not set
+# CONFIG_DEBUG_KERNEL is not set
+CONFIG_LOG_BUF_SHIFT=15
+# CONFIG_DEBUG_BUGVERBOSE is not set
+# CONFIG_FRAME_POINTER is not set
+
+#
+# Security options
+#
+# CONFIG_KEYS is not set
+# CONFIG_SECURITY is not set
+
+#
+# Cryptographic options
+#
+# CONFIG_CRYPTO is not set
+
+#
+# Hardware crypto devices
+#
+
+#
+# Library routines
+#
+# CONFIG_CRC_CCITT is not set
+CONFIG_CRC32=y
+# CONFIG_LIBCRC32C is not set
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=y
diff --git a/arch/m32r/mappi3/dot.gdbinit b/arch/m32r/mappi3/dot.gdbinit
new file mode 100644
index 0000000..89c2218
--- /dev/null
+++ b/arch/m32r/mappi3/dot.gdbinit
@@ -0,0 +1,224 @@
+# .gdbinit file
+# $Id: dot.gdbinit,v 1.1 2005/04/11 02:21:08 sakugawa Exp $
+
+# setting
+set width 0d70
+set radix 0d16
+use_debug_dma
+
+# Initialize SDRAM controller for Mappi
+define sdram_init
+  # SDIR0
+  set *(unsigned long *)0x00ef6008 = 0x00000182
+  # SDIR1
+  set *(unsigned long *)0x00ef600c = 0x00000001
+  # Initialize wait
+  shell sleep 0.1
+  # MOD
+  set *(unsigned long *)0x00ef602c = 0x00000020
+  set *(unsigned long *)0x00ef604c = 0x00000020
+  # TR
+  set *(unsigned long *)0x00ef6028 = 0x00051502
+  set *(unsigned long *)0x00ef6048 = 0x00051502
+  # ADR
+  set *(unsigned long *)0x00ef6020 = 0x08000004
+  set *(unsigned long *)0x00ef6040 = 0x0c000004
+  # AutoRef On
+  set *(unsigned long *)0x00ef6004 = 0x00010517
+  # Access enable
+  set *(unsigned long *)0x00ef6024 = 0x00000001
+  set *(unsigned long *)0x00ef6044 = 0x00000001
+end
+
+# Initialize LAN controller for Mappi
+define lanc_init
+  # Set BSEL4
+  #set *(unsigned long *)0x00ef5004 = 0x0fff330f
+  #set *(unsigned long *)0x00ef5004 = 0x01113301
+
+#  set *(unsigned long *)0x00ef5004 = 0x02011101
+#  set *(unsigned long *)0x00ef5004 = 0x04441104
+end
+
+define clock_init
+  set *(unsigned long *)0x00ef4010 = 2
+  set *(unsigned long *)0x00ef4014 = 2
+  set *(unsigned long *)0x00ef4020 = 3
+  set *(unsigned long *)0x00ef4024 = 3
+  set *(unsigned long *)0x00ef4004 = 0x7
+#  shell sleep 0.1
+#  set *(unsigned long *)0x00ef4004 = 0x5
+  shell sleep 0.1
+  set *(unsigned long *)0x00ef4008 = 0x0200
+end
+
+define port_init
+  set $sfrbase = 0x00ef0000
+  set *(unsigned short *)0x00ef1060 = 0x5555
+  set *(unsigned short *)0x00ef1062 = 0x5555
+  set *(unsigned short *)0x00ef1064 = 0x5555
+  set *(unsigned short *)0x00ef1066 = 0x5555
+  set *(unsigned short *)0x00ef1068 = 0x5555
+  set *(unsigned short *)0x00ef106a = 0x0000
+  set *(unsigned short *)0x00ef106e = 0x5555
+  set *(unsigned short *)0x00ef1070 = 0x5555
+end
+
+# MMU enable
+define mmu_enable
+  set $evb=0x88000000
+  set *(unsigned long *)0xffff0024=1
+end
+
+# MMU disable
+define mmu_disable
+  set $evb=0
+  set *(unsigned long *)0xffff0024=0
+end
+
+# Show TLB entries
+define show_tlb_entries
+  set $i = 0
+  set $addr = $arg0
+  while ($i < 0d16 )
+    set $tlb_tag = *(unsigned long*)$addr
+    set $tlb_data = *(unsigned long*)($addr + 4)
+    printf " [%2d] 0x%08lx : 0x%08lx - 0x%08lx\n", $i, $addr, $tlb_tag, $tlb_data
+    set $i = $i + 1
+    set $addr = $addr + 8
+  end
+end
+define itlb
+  set $itlb=0xfe000000
+  show_tlb_entries $itlb
+end
+define dtlb
+  set $dtlb=0xfe000800
+  show_tlb_entries $dtlb
+end
+
+# Cache ON
+define set_cache_type
+  set $mctype = (void*)0xfffffff8
+# chaos
+# set *(unsigned long *)($mctype) = 0x0000c000
+# m32102 i-cache only
+  set *(unsigned long *)($mctype) = 0x00008000
+# m32102 d-cache only
+#  set *(unsigned long *)($mctype) = 0x00004000
+end
+define cache_on
+  set $param = (void*)0x08001000
+  set *(unsigned long *)($param) = 0x60ff6102
+end
+
+
+# Show current task structure
+define show_current
+  set $current = $spi & 0xffffe000
+  printf "$current=0x%08lX\n",$current
+  print *(struct task_struct *)$current
+end
+
+# Show user assigned task structure
+define show_task
+  set $task = $arg0 & 0xffffe000
+  printf "$task=0x%08lX\n",$task
+  print *(struct task_struct *)$task
+end
+document show_task
+  Show user assigned task structure
+  arg0 : task structure address
+end
+
+# Show M32R registers
+define show_regs
+  printf " R0[0x%08lX]   R1[0x%08lX]   R2[0x%08lX]   R3[0x%08lX]\n",$r0,$r1,$r2,$r3
+  printf " R4[0x%08lX]   R5[0x%08lX]   R6[0x%08lX]   R7[0x%08lX]\n",$r4,$r5,$r6,$r7
+  printf " R8[0x%08lX]   R9[0x%08lX]  R10[0x%08lX]  R11[0x%08lX]\n",$r8,$r9,$r10,$r11
+  printf "R12[0x%08lX]   FP[0x%08lX]   LR[0x%08lX]   SP[0x%08lX]\n",$r12,$fp,$lr,$sp
+  printf "PSW[0x%08lX]  CBR[0x%08lX]  SPI[0x%08lX]  SPU[0x%08lX]\n",$psw,$cbr,$spi,$spu
+  printf "BPC[0x%08lX]   PC[0x%08lX] ACCL[0x%08lX] ACCH[0x%08lX]\n",$bpc,$pc,$accl,$acch
+  printf "EVB[0x%08lX]\n",$evb
+
+  set $mests = *(unsigned long *)0xffff000c
+  set $mdeva = *(unsigned long *)0xffff0010
+  printf "MESTS[0x%08lX] MDEVA[0x%08lX]\n",$mests,$mdeva
+end
+
+
+# Setup all
+define setup
+  clock_init
+  shell sleep 0.1
+  port_init
+  sdram_init
+#  lanc_init
+#  dispc_init
+#  set $evb=0x08000000
+end
+
+# Load modules
+define load_modules
+  use_debug_dma
+  load
+#  load busybox.mot
+end
+
+# Set kernel parameters
+define set_kernel_parameters
+  set $param = (void*)0x08001000
+
+  ## MOUNT_ROOT_RDONLY
+  set {long}($param+0x00)=0
+  ## RAMDISK_FLAGS
+  #set {long}($param+0x04)=0
+  ## ORIG_ROOT_DEV
+  #set {long}($param+0x08)=0x00000100
+  ## LOADER_TYPE
+  #set {long}($param+0x0C)=0
+  ## INITRD_START
+  set {long}($param+0x10)=0x082a0000
+  ## INITRD_SIZE
+  set {long}($param+0x14)=0d6200000
+
+  # M32R_CPUCLK
+  set *(unsigned long *)($param + 0x0018) = 0d100000000
+  # M32R_BUSCLK
+  set *(unsigned long *)($param + 0x001c) = 0d50000000
+  # M32R_TIMER_DIVIDE
+  set *(unsigned long *)($param + 0x0020) = 0d128
+
+
+ set {char[0x200]}($param + 0x100) = "console=ttyS0,115200n8x root=/dev/nfsroot nfsroot=192.168.0.1:/project/m32r-linux/export/root.2.6_04 nfsaddrs=192.168.0.102:192.168.0.1:192.168.0.1:255.255.255.0:mappi: \0"
+
+
+end
+
+# Boot
+define boot
+  set_kernel_parameters
+  debug_chaos
+  set *(unsigned long *)0x00f00000=0x08002000
+  set $pc=0x08002000
+  set $fp=0
+  del b
+  si
+end
+
+# Restart
+define restart
+  sdireset
+  sdireset
+  setup
+  load_modules
+  boot
+end
+
+sdireset
+sdireset
+file vmlinux
+target m32rsdi
+
+restart
+boot
diff --git a/arch/m32r/mm/extable.c b/arch/m32r/mm/extable.c
index 9a97363..1743f23 100644
--- a/arch/m32r/mm/extable.c
+++ b/arch/m32r/mm/extable.c
@@ -1,10 +1,8 @@
 /*
- * linux/arch/i386/mm/extable.c
+ * linux/arch/m32r/mm/extable.c
  */
 
-#include <linux/config.h>
 #include <linux/module.h>
-#include <linux/spinlock.h>
 #include <asm/uaccess.h>
 
 int fixup_exception(struct pt_regs *regs)
@@ -19,4 +17,3 @@
 
 	return 0;
 }
-
diff --git a/arch/m32r/oaks32r/defconfig.nommu b/arch/m32r/oaks32r/defconfig.nommu
index f2da9be..3f9fe51 100644
--- a/arch/m32r/oaks32r/defconfig.nommu
+++ b/arch/m32r/oaks32r/defconfig.nommu
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:11:13 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:22:04 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -16,6 +16,7 @@
 CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
 CONFIG_LOCK_KERNEL=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -26,12 +27,14 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 # CONFIG_IKCONFIG is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -40,6 +43,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 CONFIG_TINY_SHMEM=y
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -61,6 +65,7 @@
 # CONFIG_PLAT_OPSPUT is not set
 CONFIG_PLAT_OAKS32R=y
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 # CONFIG_CHIP_M32700 is not set
 CONFIG_CHIP_M32102=y
 # CONFIG_CHIP_VDEC2 is not set
@@ -92,10 +97,6 @@
 # CONFIG_PCCARD is not set
 
 #
-# PC-card bridges
-#
-
-#
 # PCI Hotplug Support
 #
 
@@ -193,7 +194,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -311,18 +311,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -332,6 +320,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 # CONFIG_VT is not set
@@ -375,6 +374,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -415,10 +418,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -574,8 +573,9 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 # CONFIG_DEBUG_KERNEL is not set
-CONFIG_DEBUG_PREEMPT=y
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_DEBUG_BUGVERBOSE is not set
 # CONFIG_FRAME_POINTER is not set
 
diff --git a/arch/m32r/opsput/defconfig.opsput b/arch/m32r/opsput/defconfig.opsput
index a87e1ea..66adec6 100644
--- a/arch/m32r/opsput/defconfig.opsput
+++ b/arch/m32r/opsput/defconfig.opsput
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.11-rc4
-# Wed Feb 16 21:11:41 2005
+# Linux kernel version: 2.6.12-rc5
+# Fri Jun  3 16:22:06 2005
 #
 CONFIG_M32R=y
 # CONFIG_UID16 is not set
@@ -15,6 +15,7 @@
 CONFIG_EXPERIMENTAL=y
 CONFIG_CLEAN_COMPILE=y
 CONFIG_BROKEN_ON_SMP=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
 
 #
 # General setup
@@ -27,13 +28,15 @@
 # CONFIG_BSD_PROCESS_ACCT_V3 is not set
 CONFIG_SYSCTL=y
 # CONFIG_AUDIT is not set
-CONFIG_LOG_BUF_SHIFT=14
 CONFIG_HOTPLUG=y
 CONFIG_KOBJECT_UEVENT=y
 CONFIG_IKCONFIG=y
 # CONFIG_IKCONFIG_PROC is not set
 CONFIG_EMBEDDED=y
 # CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
 # CONFIG_FUTEX is not set
 # CONFIG_EPOLL is not set
 # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
@@ -43,6 +46,7 @@
 CONFIG_CC_ALIGN_LOOPS=0
 CONFIG_CC_ALIGN_JUMPS=0
 # CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
 
 #
 # Loadable module support
@@ -64,6 +68,7 @@
 CONFIG_PLAT_OPSPUT=y
 # CONFIG_PLAT_OAKS32R is not set
 # CONFIG_PLAT_MAPPI2 is not set
+# CONFIG_PLAT_MAPPI3 is not set
 # CONFIG_CHIP_M32700 is not set
 # CONFIG_CHIP_M32102 is not set
 # CONFIG_CHIP_VDEC2 is not set
@@ -243,7 +248,6 @@
 #
 CONFIG_PACKET=y
 # CONFIG_PACKET_MMAP is not set
-# CONFIG_NETLINK_DEV is not set
 CONFIG_UNIX=y
 # CONFIG_NET_KEY is not set
 CONFIG_INET=y
@@ -368,18 +372,6 @@
 # CONFIG_INPUT_EVBUG is not set
 
 #
-# Input I/O drivers
-#
-# CONFIG_GAMEPORT is not set
-CONFIG_SOUND_GAMEPORT=y
-CONFIG_SERIO=y
-# CONFIG_SERIO_I8042 is not set
-CONFIG_SERIO_SERPORT=y
-# CONFIG_SERIO_CT82C710 is not set
-# CONFIG_SERIO_LIBPS2 is not set
-# CONFIG_SERIO_RAW is not set
-
-#
 # Input Device Drivers
 #
 # CONFIG_INPUT_KEYBOARD is not set
@@ -389,6 +381,17 @@
 # CONFIG_INPUT_MISC is not set
 
 #
+# Hardware I/O ports
+#
+CONFIG_SERIO=y
+# CONFIG_SERIO_I8042 is not set
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_LIBPS2 is not set
+# CONFIG_SERIO_RAW is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
 # Character devices
 #
 # CONFIG_VT is not set
@@ -438,6 +441,10 @@
 # CONFIG_RAW_DRIVER is not set
 
 #
+# TPM devices
+#
+
+#
 # I2C support
 #
 # CONFIG_I2C is not set
@@ -478,10 +485,6 @@
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 
 #
-# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' may also be needed; see USB_STORAGE Help for more information
-#
-
-#
 # USB Gadget Support
 #
 # CONFIG_USB_GADGET is not set
@@ -654,8 +657,10 @@
 #
 # Kernel hacking
 #
+# CONFIG_PRINTK_TIME is not set
 CONFIG_DEBUG_KERNEL=y
 # CONFIG_MAGIC_SYSRQ is not set
+CONFIG_LOG_BUF_SHIFT=14
 # CONFIG_SCHEDSTATS is not set
 # CONFIG_DEBUG_SLAB is not set
 # CONFIG_DEBUG_SPINLOCK is not set
diff --git a/arch/mips/mm/init.c b/arch/mips/mm/init.c
index b027ce7..73843c5 100644
--- a/arch/mips/mm/init.c
+++ b/arch/mips/mm/init.c
@@ -232,7 +232,6 @@
 #ifdef CONFIG_LIMITED_DMA
 		set_page_address(page, lowmem_page_address(page));
 #endif
-		set_bit(PG_highmem, &page->flags);
 		set_page_count(page, 1);
 		__free_page(page);
 		totalhigh_pages++;
diff --git a/arch/ppc/Kconfig b/arch/ppc/Kconfig
index 54ce6da..10162b1 100644
--- a/arch/ppc/Kconfig
+++ b/arch/ppc/Kconfig
@@ -826,11 +826,6 @@
 	depends on PCORE || POWERPMC250 || LOPEC || SANDPOINT
 	default y
 
-config FSL_OCP
-	bool
-	depends on MPC10X_BRIDGE
-	default y
-
 config MPC10X_OPENPIC
 	bool
 	depends on POWERPMC250 || LOPEC || SANDPOINT
diff --git a/arch/ppc/boot/ld.script b/arch/ppc/boot/ld.script
index 6ee602d..9362193 100644
--- a/arch/ppc/boot/ld.script
+++ b/arch/ppc/boot/ld.script
@@ -58,9 +58,6 @@
     *(.ramdisk)
     __ramdisk_end = .;
     . = ALIGN(4096);
-    __sysmap_begin = .;
-    *(.sysmap)
-    __sysmap_end = .;
     CONSTRUCTORS
   }
   _edata  =  .;
diff --git a/arch/ppc/boot/openfirmware/Makefile b/arch/ppc/boot/openfirmware/Makefile
index 4eacbd8..0341523 100644
--- a/arch/ppc/boot/openfirmware/Makefile
+++ b/arch/ppc/boot/openfirmware/Makefile
@@ -54,13 +54,10 @@
 	@echo '          RAM disk image must be provided separately'
 	@/bin/false
 
-objcpxmon-$(CONFIG_XMON) := --add-section=.sysmap=System.map \
-	--set-section-flags=.sysmap=contents,alloc,load,readonly,data
 quiet_cmd_genimage = GEN     $@
       cmd_genimage = $(OBJCOPY) -R .comment       \
 	--add-section=.image=$(images)/vmlinux.gz \
-	--set-section-flags=.image=contents,alloc,load,readonly,data \
-	$(objcpxmon-y) $< $@
+	--set-section-flags=.image=contents,alloc,load,readonly,data $< $@
 
 targets += image.o
 $(obj)/image.o: $(obj)/dummy.o $(images)/vmlinux.gz FORCE
diff --git a/arch/ppc/boot/openfirmware/common.c b/arch/ppc/boot/openfirmware/common.c
index 9e69527..0f46756 100644
--- a/arch/ppc/boot/openfirmware/common.c
+++ b/arch/ppc/boot/openfirmware/common.c
@@ -15,7 +15,6 @@
 #include <asm/page.h>
 
 /* Information from the linker */
-extern char __sysmap_begin, __sysmap_end;
 
 extern int strcmp(const char *s1, const char *s2);
 extern char *avail_ram, *avail_high;
@@ -116,14 +115,8 @@
 void make_bi_recs(unsigned long addr, char *name, unsigned int mach,
 		unsigned long progend)
 {
-	unsigned long sysmap_size;
 	struct bi_record *rec;
 
-	/* Figure out the size of a possible System.map we're going to
-	 * pass along.
-	 * */
-	sysmap_size = (unsigned long)(&__sysmap_end) -
-		(unsigned long)(&__sysmap_begin);
 
 	/* leave a 1MB gap then align to the next 1MB boundary */
 	addr = _ALIGN(addr+ (1<<20) - 1, (1<<20));
@@ -147,15 +140,6 @@
 	rec->size = sizeof(struct bi_record) + 2 * sizeof(unsigned long);
 	rec = (struct bi_record *)((unsigned long)rec + rec->size);
 
-	if (sysmap_size) {
-		rec->tag = BI_SYSMAP;
-		rec->data[0] = (unsigned long)(&__sysmap_begin);
-		rec->data[1] = sysmap_size;
-		rec->size = sizeof(struct bi_record) + 2 *
-			sizeof(unsigned long);
-		rec = (struct bi_record *)((unsigned long)rec + rec->size);
-	}
-
 	rec->tag = BI_LAST;
 	rec->size = sizeof(struct bi_record);
 	rec = (struct bi_record *)((unsigned long)rec + rec->size);
diff --git a/arch/ppc/boot/simple/Makefile b/arch/ppc/boot/simple/Makefile
index c28061a..991b4cb 100644
--- a/arch/ppc/boot/simple/Makefile
+++ b/arch/ppc/boot/simple/Makefile
@@ -203,7 +203,7 @@
 		$(obj)/dummy.o $(obj)/image.o
 	$(LD) $(LD_ARGS) -o $@ $(OBJS) $(obj)/image.o $(LIBS)
 	$(OBJCOPY) $(OBJCOPY_ARGS) $@ $@ -R .comment -R .stab \
-		-R .stabstr -R .ramdisk -R .sysmap
+		-R .stabstr -R .ramdisk
 
 $(obj)/zvmlinux.initrd: $(OBJS) $(LIBS) $(srctree)/$(boot)/ld.script \
 		$(images)/vmlinux.gz $(obj)/dummy.o
@@ -215,7 +215,7 @@
 		$(obj)/dummy.o $(obj)/image.o
 	$(LD) $(LD_ARGS) -o $@ $(OBJS) $(obj)/image.o $(LIBS)
 	$(OBJCOPY) $(OBJCOPY_ARGS) $@ $@ -R .comment -R .stab \
-		-R .stabstr -R .sysmap
+		-R .stabstr
 
 # Sort-of dummy rules, that let us format the image we want.
 zImage: $(images)/$(zimage-y) $(obj)/zvmlinux
diff --git a/arch/ppc/boot/utils/addSystemMap.c b/arch/ppc/boot/utils/addSystemMap.c
deleted file mode 100644
index 4654f89..0000000
--- a/arch/ppc/boot/utils/addSystemMap.c
+++ /dev/null
@@ -1,186 +0,0 @@
-#include <stdio.h>
-#include <stdlib.h>
-#include <byteswap.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-
-void xlate( char * inb, char * trb, unsigned len )
-{
-    unsigned i;
-    for (  i=0; i<len; ++i ) {
-	char c = *inb++;
-	char c1 = c >> 4;
-	char c2 = c & 0xf;
-	if ( c1 > 9 )
-	    c1 = c1 + 'A' - 10;
-	else
-	    c1 = c1 + '0';
-	if ( c2 > 9 )
-	    c2 = c2 + 'A' - 10;
-	else
-	    c2 = c2 + '0';
-	*trb++ = c1;
-	*trb++ = c2;
-    }
-    *trb = 0;
-}
-
-#define ElfHeaderSize  (64 * 1024)
-#define ElfPages  (ElfHeaderSize / 4096)
-#define KERNELBASE (0xc0000000)
-
-void get4k( /*istream *inf*/FILE *file, char *buf )
-{
-    unsigned j;
-    unsigned num = fread(buf, 1, 4096, file);
-    for (  j=num; j<4096; ++j )
-	buf[j] = 0;
-}
-
-void put4k( /*ostream *outf*/FILE *file, char *buf )
-{
-    fwrite(buf, 1, 4096, file);
-}
-
-int main(int argc, char **argv)
-{
-    char inbuf[4096];
-    FILE *ramDisk = NULL;
-    FILE *inputVmlinux = NULL;
-    FILE *outputVmlinux = NULL;
-    unsigned i = 0;
-    unsigned long ramFileLen = 0;
-    unsigned long ramLen = 0;
-    unsigned long roundR = 0;
-    unsigned long kernelLen = 0;
-    unsigned long actualKernelLen = 0;
-    unsigned long round = 0;
-    unsigned long roundedKernelLen = 0;
-    unsigned long ramStartOffs = 0;
-    unsigned long ramPages = 0;
-    unsigned long roundedKernelPages = 0;
-    if ( argc < 2 ) {
-	printf("Name of System Map file missing.\n");
-	exit(1);
-    }
-
-    if ( argc < 3 ) {
-	printf("Name of vmlinux file missing.\n");
-	exit(1);
-    }
-
-    if ( argc < 4 ) {
-	printf("Name of vmlinux output file missing.\n");
-	exit(1);
-    }
-
-    ramDisk = fopen(argv[1], "r");
-    if ( ! ramDisk ) {
-	printf("System Map file \"%s\" failed to open.\n", argv[1]);
-	exit(1);
-    }
-    inputVmlinux = fopen(argv[2], "r");
-    if ( ! inputVmlinux ) {
-	printf("vmlinux file \"%s\" failed to open.\n", argv[2]);
-	exit(1);
-    }
-    outputVmlinux = fopen(argv[3], "w");
-    if ( ! outputVmlinux ) {
-	printf("output vmlinux file \"%s\" failed to open.\n", argv[3]);
-	exit(1);
-    }
-    fseek(ramDisk, 0, SEEK_END);
-    ramFileLen = ftell(ramDisk);
-    fseek(ramDisk, 0, SEEK_SET);
-    printf("%s file size = %ld\n", argv[1], ramFileLen);
-
-    ramLen = ramFileLen;
-
-    roundR = 4096 - (ramLen % 4096);
-    if ( roundR ) {
-	printf("Rounding System Map file up to a multiple of 4096, adding %ld\n", roundR);
-	ramLen += roundR;
-    }
-
-    printf("Rounded System Map size is %ld\n", ramLen);
-    fseek(inputVmlinux, 0, SEEK_END);
-    kernelLen = ftell(inputVmlinux);
-    fseek(inputVmlinux, 0, SEEK_SET);
-    printf("kernel file size = %ld\n", kernelLen);
-    if ( kernelLen == 0 ) {
-	printf("You must have a linux kernel specified as argv[2]\n");
-	exit(1);
-    }
-
-    actualKernelLen = kernelLen - ElfHeaderSize;
-
-    printf("actual kernel length (minus ELF header) = %ld\n", actualKernelLen);
-
-    round = actualKernelLen % 4096;
-    roundedKernelLen = actualKernelLen;
-    if ( round )
-	roundedKernelLen += (4096 - round);
-
-    printf("actual kernel length rounded up to a 4k multiple = %ld\n", roundedKernelLen);
-
-    ramStartOffs = roundedKernelLen;
-    ramPages = ramLen / 4096;
-
-    printf("System map pages to copy = %ld\n", ramPages);
-
-    // Copy 64K ELF header
-      for (i=0; i<(ElfPages); ++i) {
-	  get4k( inputVmlinux, inbuf );
-	  put4k( outputVmlinux, inbuf );
-      }
-
-
-
-    roundedKernelPages = roundedKernelLen / 4096;
-
-    fseek(inputVmlinux, ElfHeaderSize, SEEK_SET);
-
-    {
-	for ( i=0; i<roundedKernelPages; ++i ) {
-	    get4k( inputVmlinux, inbuf );
-	    if ( i == 0 ) {
-		unsigned long * p;
-		printf("Storing embedded_sysmap_start at 0x3c\n");
-		p = (unsigned long *)(inbuf + 0x3c);
-
-#if (BYTE_ORDER == __BIG_ENDIAN)
-		*p = ramStartOffs;
-#else
-		*p = bswap_32(ramStartOffs);
-#endif
-
-		printf("Storing embedded_sysmap_end at 0x44\n");
-		p = (unsigned long *)(inbuf + 0x44);
-#if (BYTE_ORDER == __BIG_ENDIAN)
-		*p = ramStartOffs + ramFileLen;
-#else
-		*p = bswap_32(ramStartOffs + ramFileLen);
-#endif
-	    }
-	    put4k( outputVmlinux, inbuf );
-	}
-    }
-
-    {
-	for ( i=0; i<ramPages; ++i ) {
-	    get4k( ramDisk, inbuf );
-	    put4k( outputVmlinux, inbuf );
-	}
-    }
-
-
-    fclose(ramDisk);
-    fclose(inputVmlinux);
-    fclose(outputVmlinux);
-    /* Set permission to executable */
-    chmod(argv[3], S_IRUSR|S_IWUSR|S_IXUSR|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
-
-    return 0;
-
-}
-
diff --git a/arch/ppc/configs/mpc8548_cds_defconfig b/arch/ppc/configs/mpc8548_cds_defconfig
new file mode 100644
index 0000000..abe034f
--- /dev/null
+++ b/arch/ppc/configs/mpc8548_cds_defconfig
@@ -0,0 +1,659 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.12-rc4
+# Tue May 24 22:36:27 2005
+#
+CONFIG_MMU=y
+CONFIG_GENERIC_HARDIRQS=y
+CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_HAVE_DEC_LOCK=y
+CONFIG_PPC=y
+CONFIG_PPC32=y
+CONFIG_GENERIC_NVRAM=y
+CONFIG_SCHED_NO_NO_OMIT_FRAME_POINTER=y
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+CONFIG_BROKEN_ON_SMP=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+# CONFIG_POSIX_MQUEUE is not set
+# CONFIG_BSD_PROCESS_ACCT is not set
+CONFIG_SYSCTL=y
+# CONFIG_AUDIT is not set
+# CONFIG_HOTPLUG is not set
+CONFIG_KOBJECT_UEVENT=y
+# CONFIG_IKCONFIG is not set
+CONFIG_EMBEDDED=y
+# CONFIG_KALLSYMS is not set
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_BASE_FULL=y
+CONFIG_FUTEX=y
+# CONFIG_EPOLL is not set
+# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
+CONFIG_SHMEM=y
+CONFIG_CC_ALIGN_FUNCTIONS=0
+CONFIG_CC_ALIGN_LABELS=0
+CONFIG_CC_ALIGN_LOOPS=0
+CONFIG_CC_ALIGN_JUMPS=0
+# CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
+
+#
+# Loadable module support
+#
+# CONFIG_MODULES is not set
+
+#
+# Processor
+#
+# CONFIG_6xx is not set
+# CONFIG_40x is not set
+# CONFIG_44x is not set
+# CONFIG_POWER3 is not set
+# CONFIG_POWER4 is not set
+# CONFIG_8xx is not set
+CONFIG_E500=y
+CONFIG_BOOKE=y
+CONFIG_FSL_BOOKE=y
+# CONFIG_PHYS_64BIT is not set
+CONFIG_SPE=y
+CONFIG_MATH_EMULATION=y
+# CONFIG_CPU_FREQ is not set
+# CONFIG_PM is not set
+CONFIG_85xx=y
+CONFIG_PPC_INDIRECT_PCI_BE=y
+
+#
+# Freescale 85xx options
+#
+# CONFIG_MPC8540_ADS is not set
+CONFIG_MPC8548_CDS=y
+# CONFIG_MPC8555_CDS is not set
+# CONFIG_MPC8560_ADS is not set
+# CONFIG_SBC8560 is not set
+# CONFIG_STX_GP3 is not set
+CONFIG_MPC8548=y
+
+#
+# Platform options
+#
+# CONFIG_SMP is not set
+# CONFIG_PREEMPT is not set
+# CONFIG_HIGHMEM is not set
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_MISC is not set
+# CONFIG_CMDLINE_BOOL is not set
+CONFIG_ISA_DMA_API=y
+
+#
+# Bus options
+#
+# CONFIG_PCI is not set
+# CONFIG_PCI_DOMAINS is not set
+
+#
+# PCCARD (PCMCIA/CardBus) support
+#
+# CONFIG_PCCARD is not set
+
+#
+# Advanced setup
+#
+# CONFIG_ADVANCED_OPTIONS is not set
+
+#
+# Default settings for advanced configuration options are used
+#
+CONFIG_HIGHMEM_START=0xfe000000
+CONFIG_LOWMEM_SIZE=0x30000000
+CONFIG_KERNEL_START=0xc0000000
+CONFIG_TASK_SIZE=0x80000000
+CONFIG_BOOT_LOAD=0x00800000
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+# CONFIG_FW_LOADER is not set
+
+#
+# Memory Technology Devices (MTD)
+#
+# CONFIG_MTD is not set
+
+#
+# Parallel port support
+#
+# CONFIG_PARPORT is not set
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_BLK_DEV_FD is not set
+# CONFIG_BLK_DEV_COW_COMMON is not set
+CONFIG_BLK_DEV_LOOP=y
+# CONFIG_BLK_DEV_CRYPTOLOOP is not set
+# CONFIG_BLK_DEV_NBD is not set
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_COUNT=16
+CONFIG_BLK_DEV_RAM_SIZE=32768
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_INITRAMFS_SOURCE=""
+# CONFIG_LBD is not set
+# CONFIG_CDROM_PKTCDVD is not set
+
+#
+# IO Schedulers
+#
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+CONFIG_IOSCHED_CFQ=y
+# CONFIG_ATA_OVER_ETH is not set
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+# CONFIG_IDE is not set
+
+#
+# SCSI device support
+#
+# CONFIG_SCSI is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+# CONFIG_MD is not set
+
+#
+# Fusion MPT device support
+#
+
+#
+# IEEE 1394 (FireWire) support
+#
+
+#
+# I2O device support
+#
+
+#
+# Macintosh device drivers
+#
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+# CONFIG_PACKET_MMAP is not set
+CONFIG_UNIX=y
+# CONFIG_NET_KEY is not set
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+# CONFIG_IP_ADVANCED_ROUTER is not set
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+CONFIG_IP_PNP_BOOTP=y
+# CONFIG_IP_PNP_RARP is not set
+# CONFIG_NET_IPIP is not set
+# CONFIG_NET_IPGRE is not set
+# CONFIG_IP_MROUTE is not set
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+# CONFIG_INET_AH is not set
+# CONFIG_INET_ESP is not set
+# CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_TUNNEL is not set
+CONFIG_IP_TCPDIAG=y
+# CONFIG_IP_TCPDIAG_IPV6 is not set
+# CONFIG_IPV6 is not set
+# CONFIG_NETFILTER is not set
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_SCTP is not set
+# CONFIG_ATM is not set
+# CONFIG_BRIDGE is not set
+# CONFIG_VLAN_8021Q is not set
+# CONFIG_DECNET is not set
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+# CONFIG_NET_DIVERT is not set
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+# CONFIG_NET_SCHED is not set
+# CONFIG_NET_CLS_ROUTE is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+# CONFIG_NETPOLL is not set
+# CONFIG_NET_POLL_CONTROLLER is not set
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+# CONFIG_BT is not set
+CONFIG_NETDEVICES=y
+# CONFIG_DUMMY is not set
+# CONFIG_BONDING is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_TUN is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=y
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_GIANFAR=y
+CONFIG_GFAR_NAPI=y
+
+#
+# Ethernet (10000 Mbit)
+#
+
+#
+# Token Ring devices
+#
+
+#
+# Wireless LAN (non-hamradio)
+#
+# CONFIG_NET_RADIO is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+# CONFIG_PPP is not set
+# CONFIG_SLIP is not set
+# CONFIG_SHAPER is not set
+# CONFIG_NETCONSOLE is not set
+
+#
+# ISDN subsystem
+#
+# CONFIG_ISDN is not set
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+# CONFIG_INPUT_MOUSEDEV is not set
+# CONFIG_INPUT_JOYDEV is not set
+# CONFIG_INPUT_TSDEV is not set
+# CONFIG_INPUT_EVDEV is not set
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input Device Drivers
+#
+# CONFIG_INPUT_KEYBOARD is not set
+# CONFIG_INPUT_MOUSE is not set
+# CONFIG_INPUT_JOYSTICK is not set
+# CONFIG_INPUT_TOUCHSCREEN is not set
+# CONFIG_INPUT_MISC is not set
+
+#
+# Hardware I/O ports
+#
+# CONFIG_SERIO is not set
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+
+#
+# Character devices
+#
+# CONFIG_VT is not set
+# CONFIG_SERIAL_NONSTANDARD is not set
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_NR_UARTS=4
+# CONFIG_SERIAL_8250_EXTENDED is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+CONFIG_LEGACY_PTYS=y
+CONFIG_LEGACY_PTY_COUNT=256
+
+#
+# IPMI
+#
+# CONFIG_IPMI_HANDLER is not set
+
+#
+# Watchdog Cards
+#
+# CONFIG_WATCHDOG is not set
+# CONFIG_NVRAM is not set
+CONFIG_GEN_RTC=y
+# CONFIG_GEN_RTC_X is not set
+# CONFIG_DTLK is not set
+# CONFIG_R3964 is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+# CONFIG_AGP is not set
+# CONFIG_DRM is not set
+# CONFIG_RAW_DRIVER is not set
+
+#
+# TPM devices
+#
+
+#
+# I2C support
+#
+CONFIG_I2C=y
+CONFIG_I2C_CHARDEV=y
+
+#
+# I2C Algorithms
+#
+# CONFIG_I2C_ALGOBIT is not set
+# CONFIG_I2C_ALGOPCF is not set
+# CONFIG_I2C_ALGOPCA is not set
+
+#
+# I2C Hardware Bus support
+#
+# CONFIG_I2C_ISA is not set
+CONFIG_I2C_MPC=y
+# CONFIG_I2C_PARPORT_LIGHT is not set
+# CONFIG_I2C_PCA_ISA is not set
+
+#
+# Hardware Sensors Chip support
+#
+# CONFIG_I2C_SENSOR is not set
+# CONFIG_SENSORS_ADM1021 is not set
+# CONFIG_SENSORS_ADM1025 is not set
+# CONFIG_SENSORS_ADM1026 is not set
+# CONFIG_SENSORS_ADM1031 is not set
+# CONFIG_SENSORS_ASB100 is not set
+# CONFIG_SENSORS_DS1621 is not set
+# CONFIG_SENSORS_FSCHER is not set
+# CONFIG_SENSORS_FSCPOS is not set
+# CONFIG_SENSORS_GL518SM is not set
+# CONFIG_SENSORS_GL520SM is not set
+# CONFIG_SENSORS_IT87 is not set
+# CONFIG_SENSORS_LM63 is not set
+# CONFIG_SENSORS_LM75 is not set
+# CONFIG_SENSORS_LM77 is not set
+# CONFIG_SENSORS_LM78 is not set
+# CONFIG_SENSORS_LM80 is not set
+# CONFIG_SENSORS_LM83 is not set
+# CONFIG_SENSORS_LM85 is not set
+# CONFIG_SENSORS_LM87 is not set
+# CONFIG_SENSORS_LM90 is not set
+# CONFIG_SENSORS_LM92 is not set
+# CONFIG_SENSORS_MAX1619 is not set
+# CONFIG_SENSORS_PC87360 is not set
+# CONFIG_SENSORS_SMSC47B397 is not set
+# CONFIG_SENSORS_SMSC47M1 is not set
+# CONFIG_SENSORS_W83781D is not set
+# CONFIG_SENSORS_W83L785TS is not set
+# CONFIG_SENSORS_W83627HF is not set
+
+#
+# Other I2C Chip support
+#
+# CONFIG_SENSORS_DS1337 is not set
+# CONFIG_SENSORS_EEPROM is not set
+# CONFIG_SENSORS_PCF8574 is not set
+# CONFIG_SENSORS_PCF8591 is not set
+# CONFIG_SENSORS_RTC8564 is not set
+# CONFIG_SENSORS_M41T00 is not set
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_ALGO is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Misc devices
+#
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+
+#
+# Graphics support
+#
+# CONFIG_FB is not set
+
+#
+# Sound
+#
+# CONFIG_SOUND is not set
+
+#
+# USB support
+#
+# CONFIG_USB_ARCH_HAS_HCD is not set
+# CONFIG_USB_ARCH_HAS_OHCI is not set
+
+#
+# USB Gadget Support
+#
+# CONFIG_USB_GADGET is not set
+
+#
+# MMC/SD Card support
+#
+# CONFIG_MMC is not set
+
+#
+# InfiniBand support
+#
+# CONFIG_INFINIBAND is not set
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+# CONFIG_EXT2_FS_XATTR is not set
+CONFIG_EXT3_FS=y
+CONFIG_EXT3_FS_XATTR=y
+# CONFIG_EXT3_FS_POSIX_ACL is not set
+# CONFIG_EXT3_FS_SECURITY is not set
+CONFIG_JBD=y
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+
+#
+# XFS support
+#
+# CONFIG_XFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+# CONFIG_QUOTA is not set
+CONFIG_DNOTIFY=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_AUTOFS4_FS is not set
+
+#
+# CD-ROM/DVD Filesystems
+#
+# CONFIG_ISO9660_FS is not set
+# CONFIG_UDF_FS is not set
+
+#
+# DOS/FAT/NT Filesystems
+#
+# CONFIG_MSDOS_FS is not set
+# CONFIG_VFAT_FS is not set
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+CONFIG_SYSFS=y
+# CONFIG_DEVFS_FS is not set
+# CONFIG_DEVPTS_FS_XATTR is not set
+CONFIG_TMPFS=y
+# CONFIG_TMPFS_XATTR is not set
+# CONFIG_HUGETLB_PAGE is not set
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_HFS_FS is not set
+# CONFIG_HFSPLUS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_CRAMFS is not set
+# CONFIG_VXFS_FS is not set
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=y
+# CONFIG_NFS_V3 is not set
+# CONFIG_NFS_V4 is not set
+# CONFIG_NFS_DIRECTIO is not set
+# CONFIG_NFSD is not set
+CONFIG_ROOT_NFS=y
+CONFIG_LOCKD=y
+CONFIG_SUNRPC=y
+# CONFIG_RPCSEC_GSS_KRB5 is not set
+# CONFIG_RPCSEC_GSS_SPKM3 is not set
+# CONFIG_SMB_FS is not set
+# CONFIG_CIFS is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+# CONFIG_OSF_PARTITION is not set
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+# CONFIG_MAC_PARTITION is not set
+# CONFIG_MSDOS_PARTITION is not set
+# CONFIG_LDM_PARTITION is not set
+# CONFIG_SGI_PARTITION is not set
+# CONFIG_ULTRIX_PARTITION is not set
+# CONFIG_SUN_PARTITION is not set
+# CONFIG_EFI_PARTITION is not set
+
+#
+# Native Language Support
+#
+# CONFIG_NLS is not set
+
+#
+# Library routines
+#
+# CONFIG_CRC_CCITT is not set
+CONFIG_CRC32=y
+# CONFIG_LIBCRC32C is not set
+
+#
+# Profiling support
+#
+# CONFIG_PROFILING is not set
+
+#
+# Kernel hacking
+#
+# CONFIG_PRINTK_TIME is not set
+# CONFIG_DEBUG_KERNEL is not set
+CONFIG_LOG_BUF_SHIFT=14
+
+#
+# Security options
+#
+# CONFIG_KEYS is not set
+# CONFIG_SECURITY is not set
+
+#
+# Cryptographic options
+#
+# CONFIG_CRYPTO is not set
+
+#
+# Hardware crypto devices
+#
diff --git a/arch/ppc/kernel/cputable.c b/arch/ppc/kernel/cputable.c
index d44b7dc..01c2260 100644
--- a/arch/ppc/kernel/cputable.c
+++ b/arch/ppc/kernel/cputable.c
@@ -918,6 +918,20 @@
 		.dcache_bsize		= 32,
 		.num_pmcs		= 4,
 	},
+	{ 	/* e500v2 */
+		.pvr_mask		= 0xffff0000,
+		.pvr_value		= 0x80210000,
+		.cpu_name		= "e500v2",
+		/* xxx - galak: add CPU_FTR_MAYBE_CAN_DOZE */
+		.cpu_features		= CPU_FTR_SPLIT_ID_CACHE |
+			CPU_FTR_USE_TB | CPU_FTR_BIG_PHYS,
+		.cpu_user_features	= PPC_FEATURE_32 |
+			PPC_FEATURE_HAS_MMU | PPC_FEATURE_SPE_COMP |
+			PPC_FEATURE_HAS_EFP_SINGLE | PPC_FEATURE_HAS_EFP_DOUBLE,
+		.icache_bsize		= 32,
+		.dcache_bsize		= 32,
+		.num_pmcs		= 4,
+	},
 #endif
 #if !CLASSIC_PPC
 	{	/* default match */
diff --git a/arch/ppc/kernel/entry.S b/arch/ppc/kernel/entry.S
index 6615237..8377b6c 100644
--- a/arch/ppc/kernel/entry.S
+++ b/arch/ppc/kernel/entry.S
@@ -46,26 +46,23 @@
 
 #ifdef CONFIG_BOOKE
 #include "head_booke.h"
+#define TRANSFER_TO_HANDLER_EXC_LEVEL(exc_level)	\
+	mtspr	exc_level##_SPRG,r8;			\
+	BOOKE_LOAD_EXC_LEVEL_STACK(exc_level);		\
+	lwz	r0,GPR10-INT_FRAME_SIZE(r8);		\
+	stw	r0,GPR10(r11);				\
+	lwz	r0,GPR11-INT_FRAME_SIZE(r8);		\
+	stw	r0,GPR11(r11);				\
+	mfspr	r8,exc_level##_SPRG
+
 	.globl	mcheck_transfer_to_handler
 mcheck_transfer_to_handler:
-	mtspr	MCHECK_SPRG,r8
-	BOOKE_LOAD_MCHECK_STACK
-	lwz	r0,GPR10-INT_FRAME_SIZE(r8)
-	stw	r0,GPR10(r11)
-	lwz	r0,GPR11-INT_FRAME_SIZE(r8)
-	stw	r0,GPR11(r11)
-	mfspr	r8,MCHECK_SPRG
+	TRANSFER_TO_HANDLER_EXC_LEVEL(MCHECK)
 	b	transfer_to_handler_full
 
 	.globl	crit_transfer_to_handler
 crit_transfer_to_handler:
-	mtspr	CRIT_SPRG,r8
-	BOOKE_LOAD_CRIT_STACK
-	lwz	r0,GPR10-INT_FRAME_SIZE(r8)
-	stw	r0,GPR10(r11)
-	lwz	r0,GPR11-INT_FRAME_SIZE(r8)
-	stw	r0,GPR11(r11)
-	mfspr	r8,CRIT_SPRG
+	TRANSFER_TO_HANDLER_EXC_LEVEL(CRIT)
 	/* fall through */
 #endif
 
@@ -783,99 +780,64 @@
  * time of the critical interrupt.
  *
  */
+#ifdef CONFIG_40x
+#define PPC_40x_TURN_OFF_MSR_DR						    \
+	/* avoid any possible TLB misses here by turning off MSR.DR, we	    \
+	 * assume the instructions here are mapped by a pinned TLB entry */ \
+	li	r10,MSR_IR;						    \
+	mtmsr	r10;							    \
+	isync;								    \
+	tophys(r1, r1);
+#else
+#define PPC_40x_TURN_OFF_MSR_DR
+#endif
+
+#define RET_FROM_EXC_LEVEL(exc_lvl_srr0, exc_lvl_srr1, exc_lvl_rfi)	\
+	REST_NVGPRS(r1);						\
+	lwz	r3,_MSR(r1);						\
+	andi.	r3,r3,MSR_PR;						\
+	LOAD_MSR_KERNEL(r10,MSR_KERNEL);				\
+	bne	user_exc_return;					\
+	lwz	r0,GPR0(r1);						\
+	lwz	r2,GPR2(r1);						\
+	REST_4GPRS(3, r1);						\
+	REST_2GPRS(7, r1);						\
+	lwz	r10,_XER(r1);						\
+	lwz	r11,_CTR(r1);						\
+	mtspr	SPRN_XER,r10;						\
+	mtctr	r11;							\
+	PPC405_ERR77(0,r1);						\
+	stwcx.	r0,0,r1;		/* to clear the reservation */	\
+	lwz	r11,_LINK(r1);						\
+	mtlr	r11;							\
+	lwz	r10,_CCR(r1);						\
+	mtcrf	0xff,r10;						\
+	PPC_40x_TURN_OFF_MSR_DR;					\
+	lwz	r9,_DEAR(r1);						\
+	lwz	r10,_ESR(r1);						\
+	mtspr	SPRN_DEAR,r9;						\
+	mtspr	SPRN_ESR,r10;						\
+	lwz	r11,_NIP(r1);						\
+	lwz	r12,_MSR(r1);						\
+	mtspr	exc_lvl_srr0,r11;					\
+	mtspr	exc_lvl_srr1,r12;					\
+	lwz	r9,GPR9(r1);						\
+	lwz	r12,GPR12(r1);						\
+	lwz	r10,GPR10(r1);						\
+	lwz	r11,GPR11(r1);						\
+	lwz	r1,GPR1(r1);						\
+	PPC405_ERR77_SYNC;						\
+	exc_lvl_rfi;							\
+	b	.;		/* prevent prefetch past exc_lvl_rfi */
+
 	.globl	ret_from_crit_exc
 ret_from_crit_exc:
-	REST_NVGPRS(r1)
-	lwz	r3,_MSR(r1)
-	andi.	r3,r3,MSR_PR
-	LOAD_MSR_KERNEL(r10,MSR_KERNEL)
-	bne	user_exc_return
-
-	lwz	r0,GPR0(r1)
-	lwz	r2,GPR2(r1)
-	REST_4GPRS(3, r1)
-	REST_2GPRS(7, r1)
-
-	lwz	r10,_XER(r1)
-	lwz	r11,_CTR(r1)
-	mtspr	SPRN_XER,r10
-	mtctr	r11
-
-	PPC405_ERR77(0,r1)
-	stwcx.	r0,0,r1			/* to clear the reservation */
-
-	lwz	r11,_LINK(r1)
-	mtlr	r11
-	lwz	r10,_CCR(r1)
-	mtcrf	0xff,r10
-#ifdef CONFIG_40x
-	/* avoid any possible TLB misses here by turning off MSR.DR, we
-	 * assume the instructions here are mapped by a pinned TLB entry */
-	li	r10,MSR_IR
-	mtmsr	r10
-	isync
-	tophys(r1, r1)
-#endif
-	lwz	r9,_DEAR(r1)
-	lwz	r10,_ESR(r1)
-	mtspr	SPRN_DEAR,r9
-	mtspr	SPRN_ESR,r10
-	lwz	r11,_NIP(r1)
-	lwz	r12,_MSR(r1)
-	mtspr	SPRN_CSRR0,r11
-	mtspr	SPRN_CSRR1,r12
-	lwz	r9,GPR9(r1)
-	lwz	r12,GPR12(r1)
-	lwz	r10,GPR10(r1)
-	lwz	r11,GPR11(r1)
-	lwz	r1,GPR1(r1)
-	PPC405_ERR77_SYNC
-	rfci
-	b	.		/* prevent prefetch past rfci */
+	RET_FROM_EXC_LEVEL(SPRN_CSRR0, SPRN_CSRR1, RFCI)
 
 #ifdef CONFIG_BOOKE
-/*
- * Return from a machine check interrupt, similar to a critical
- * interrupt.
- */
 	.globl	ret_from_mcheck_exc
 ret_from_mcheck_exc:
-	REST_NVGPRS(r1)
-	lwz	r3,_MSR(r1)
-	andi.	r3,r3,MSR_PR
-	LOAD_MSR_KERNEL(r10,MSR_KERNEL)
-	bne	user_exc_return
-
-	lwz	r0,GPR0(r1)
-	lwz	r2,GPR2(r1)
-	REST_4GPRS(3, r1)
-	REST_2GPRS(7, r1)
-
-	lwz	r10,_XER(r1)
-	lwz	r11,_CTR(r1)
-	mtspr	SPRN_XER,r10
-	mtctr	r11
-
-	stwcx.	r0,0,r1			/* to clear the reservation */
-
-	lwz	r11,_LINK(r1)
-	mtlr	r11
-	lwz	r10,_CCR(r1)
-	mtcrf	0xff,r10
-	lwz	r9,_DEAR(r1)
-	lwz	r10,_ESR(r1)
-	mtspr	SPRN_DEAR,r9
-	mtspr	SPRN_ESR,r10
-	lwz	r11,_NIP(r1)
-	lwz	r12,_MSR(r1)
-	mtspr	SPRN_MCSRR0,r11
-	mtspr	SPRN_MCSRR1,r12
-	lwz	r9,GPR9(r1)
-	lwz	r12,GPR12(r1)
-	lwz	r10,GPR10(r1)
-	lwz	r11,GPR11(r1)
-	lwz	r1,GPR1(r1)
-	RFMCI
+	RET_FROM_EXC_LEVEL(SPRN_MCSRR0, SPRN_MCSRR1, RFMCI)
 #endif /* CONFIG_BOOKE */
 
 /*
diff --git a/arch/ppc/kernel/head_4xx.S b/arch/ppc/kernel/head_4xx.S
index 6f5d380..23fb518 100644
--- a/arch/ppc/kernel/head_4xx.S
+++ b/arch/ppc/kernel/head_4xx.S
@@ -291,8 +291,9 @@
 	/* If we are faulting a kernel address, we have to use the
 	 * kernel page tables.
 	 */
-	andis.	r11, r10, 0x8000
-	beq	3f
+	lis	r11, TASK_SIZE@h
+	cmplw	r10, r11
+	blt+	3f
 	lis	r11, swapper_pg_dir@h
 	ori	r11, r11, swapper_pg_dir@l
 	li	r9, 0
@@ -479,8 +480,9 @@
 	/* If we are faulting a kernel address, we have to use the
 	 * kernel page tables.
 	 */
-	andis.	r11, r10, 0x8000
-	beq	3f
+	lis	r11, TASK_SIZE@h
+	cmplw	r10, r11
+	blt+	3f
 	lis	r11, swapper_pg_dir@h
 	ori	r11, r11, swapper_pg_dir@l
 	li	r9, 0
@@ -578,8 +580,9 @@
 	/* If we are faulting a kernel address, we have to use the
 	 * kernel page tables.
 	 */
-	andis.	r11, r10, 0x8000
-	beq	3f
+	lis	r11, TASK_SIZE@h
+	cmplw	r10, r11
+	blt+	3f
 	lis	r11, swapper_pg_dir@h
 	ori	r11, r11, swapper_pg_dir@l
 	li	r9, 0
diff --git a/arch/ppc/kernel/head_booke.h b/arch/ppc/kernel/head_booke.h
index f213d12..9c50f9d 100644
--- a/arch/ppc/kernel/head_booke.h
+++ b/arch/ppc/kernel/head_booke.h
@@ -67,46 +67,36 @@
 #define CRIT_STACK_TOP		(exception_stack_top)
 
 #ifdef CONFIG_SMP
-#define BOOKE_LOAD_CRIT_STACK				\
+#define BOOKE_LOAD_EXC_LEVEL_STACK(level)		\
 	mfspr	r8,SPRN_PIR;				\
 	mulli	r8,r8,BOOKE_EXCEPTION_STACK_SIZE;	\
 	neg	r8,r8;					\
-	addis	r8,r8,CRIT_STACK_TOP@ha;		\
-	addi	r8,r8,CRIT_STACK_TOP@l
-#define BOOKE_LOAD_MCHECK_STACK				\
-	mfspr	r8,SPRN_PIR;				\
-	mulli	r8,r8,BOOKE_EXCEPTION_STACK_SIZE;	\
-	neg	r8,r8;					\
-	addis	r8,r8,MCHECK_STACK_TOP@ha;		\
-	addi	r8,r8,MCHECK_STACK_TOP@l
+	addis	r8,r8,level##_STACK_TOP@ha;		\
+	addi	r8,r8,level##_STACK_TOP@l
 #else
-#define BOOKE_LOAD_CRIT_STACK				\
-	lis	r8,CRIT_STACK_TOP@h;			\
-	ori	r8,r8,CRIT_STACK_TOP@l
-#define BOOKE_LOAD_MCHECK_STACK				\
-	lis	r8,MCHECK_STACK_TOP@h;			\
-	ori	r8,r8,MCHECK_STACK_TOP@l
+#define BOOKE_LOAD_EXC_LEVEL_STACK(level)		\
+	lis	r8,level##_STACK_TOP@h;			\
+	ori	r8,r8,level##_STACK_TOP@l
 #endif
 
 /*
- * Exception prolog for critical exceptions.  This is a little different
- * from the normal exception prolog above since a critical exception
- * can potentially occur at any point during normal exception processing.
- * Thus we cannot use the same SPRG registers as the normal prolog above.
- * Instead we use a portion of the critical exception stack at low physical
- * addresses.
+ * Exception prolog for critical/machine check exceptions.  This is a
+ * little different from the normal exception prolog above since a
+ * critical/machine check exception can potentially occur at any point
+ * during normal exception processing. Thus we cannot use the same SPRG
+ * registers as the normal prolog above. Instead we use a portion of the
+ * critical/machine check exception stack at low physical addresses.
  */
-
-#define CRITICAL_EXCEPTION_PROLOG					     \
-	mtspr	CRIT_SPRG,r8;						     \
-	BOOKE_LOAD_CRIT_STACK;		/* r8 points to the crit stack */    \
+#define EXC_LEVEL_EXCEPTION_PROLOG(exc_level, exc_level_srr0, exc_level_srr1) \
+	mtspr	exc_level##_SPRG,r8;					     \
+	BOOKE_LOAD_EXC_LEVEL_STACK(exc_level);/* r8 points to the exc_level stack*/ \
 	stw	r10,GPR10-INT_FRAME_SIZE(r8);				     \
 	stw	r11,GPR11-INT_FRAME_SIZE(r8);				     \
 	mfcr	r10;			/* save CR in r10 for now	   */\
-	mfspr	r11,SPRN_CSRR1;		/* check whether user or kernel    */\
+	mfspr	r11,exc_level_srr1;	/* check whether user or kernel    */\
 	andi.	r11,r11,MSR_PR;						     \
 	mr	r11,r8;							     \
-	mfspr	r8,CRIT_SPRG;						     \
+	mfspr	r8,exc_level##_SPRG;					     \
 	beq	1f;							     \
 	/* COMING FROM USER MODE */					     \
 	mfspr	r11,SPRN_SPRG3;		/* if from user, start at top of   */\
@@ -122,9 +112,9 @@
 	stw	r12,_DEAR(r11);		/* since they may have had stuff   */\
 	mfspr	r9,SPRN_ESR;		/* in them at the point where the  */\
 	stw	r9,_ESR(r11);		/* exception was taken		   */\
-	mfspr	r12,SPRN_CSRR0;						     \
+	mfspr	r12,exc_level_srr0;					     \
 	stw	r1,GPR1(r11);						     \
-	mfspr	r9,SPRN_CSRR1;						     \
+	mfspr	r9,exc_level_srr1;					     \
 	stw	r1,0(r11);						     \
 	mr	r1,r11;							     \
 	rlwinm	r9,r9,0,14,12;		/* clear MSR_WE (necessary?)	   */\
@@ -132,45 +122,10 @@
 	SAVE_4GPRS(3, r11);						     \
 	SAVE_2GPRS(7, r11)
 
-/*
- * Exception prolog for machine check exceptions.  This is similar to
- * the critical exception prolog, except that machine check exceptions
- * have their stack.
- */
-#define MCHECK_EXCEPTION_PROLOG					     \
-	mtspr	MCHECK_SPRG,r8;						     \
-	BOOKE_LOAD_MCHECK_STACK;	/* r8 points to the mcheck stack   */\
-	stw	r10,GPR10-INT_FRAME_SIZE(r8);				     \
-	stw	r11,GPR11-INT_FRAME_SIZE(r8);				     \
-	mfcr	r10;			/* save CR in r10 for now	   */\
-	mfspr	r11,SPRN_MCSRR1;	/* check whether user or kernel    */\
-	andi.	r11,r11,MSR_PR;						     \
-	mr	r11,r8;							     \
-	mfspr	r8,MCHECK_SPRG;						     \
-	beq	1f;							     \
-	/* COMING FROM USER MODE */					     \
-	mfspr	r11,SPRN_SPRG3;		/* if from user, start at top of   */\
-	lwz	r11,THREAD_INFO-THREAD(r11); /* this thread's kernel stack */\
-	addi	r11,r11,THREAD_SIZE;					     \
-1:	subi	r11,r11,INT_FRAME_SIZE;	/* Allocate an exception frame     */\
-	stw	r10,_CCR(r11);          /* save various registers	   */\
-	stw	r12,GPR12(r11);						     \
-	stw	r9,GPR9(r11);						     \
-	mflr	r10;							     \
-	stw	r10,_LINK(r11);						     \
-	mfspr	r12,SPRN_DEAR;		/* save DEAR and ESR in the frame  */\
-	stw	r12,_DEAR(r11);		/* since they may have had stuff   */\
-	mfspr	r9,SPRN_ESR;		/* in them at the point where the  */\
-	stw	r9,_ESR(r11);		/* exception was taken		   */\
-	mfspr	r12,SPRN_MCSRR0;					     \
-	stw	r1,GPR1(r11);						     \
-	mfspr	r9,SPRN_MCSRR1;						     \
-	stw	r1,0(r11);						     \
-	mr	r1,r11;							     \
-	rlwinm	r9,r9,0,14,12;		/* clear MSR_WE (necessary?)	   */\
-	stw	r0,GPR0(r11);						     \
-	SAVE_4GPRS(3, r11);						     \
-	SAVE_2GPRS(7, r11)
+#define CRITICAL_EXCEPTION_PROLOG \
+		EXC_LEVEL_EXCEPTION_PROLOG(CRIT, SPRN_CSRR0, SPRN_CSRR1)
+#define MCHECK_EXCEPTION_PROLOG \
+		EXC_LEVEL_EXCEPTION_PROLOG(MCHECK, SPRN_MCSRR0, SPRN_MCSRR1)
 
 /*
  * Exception vectors.
@@ -237,7 +192,6 @@
 	EXC_XFER_TEMPLATE(hdlr, n+1, MSR_KERNEL, COPY_EE, transfer_to_handler, \
 			  ret_from_except)
 
-
 /* Check for a single step debug exception while in an exception
  * handler before state has been saved.  This is to catch the case
  * where an instruction that we are trying to single step causes
@@ -291,7 +245,7 @@
 	lwz	r9,GPR9(r11);						      \
 	lwz	r12,GPR12(r11);						      \
 	mtspr	CRIT_SPRG,r8;						      \
-	BOOKE_LOAD_CRIT_STACK;		/* r8 points to the crit stack */     \
+	BOOKE_LOAD_EXC_LEVEL_STACK(CRIT); /* r8 points to the debug stack */  \
 	lwz	r10,GPR10-INT_FRAME_SIZE(r8);				      \
 	lwz	r11,GPR11-INT_FRAME_SIZE(r8);				      \
 	mfspr	r8,CRIT_SPRG;						      \
diff --git a/arch/ppc/kernel/setup.c b/arch/ppc/kernel/setup.c
index 5c20266..c42f753 100644
--- a/arch/ppc/kernel/setup.c
+++ b/arch/ppc/kernel/setup.c
@@ -41,7 +41,7 @@
 #include <asm/xmon.h>
 #include <asm/ocp.h>
 
-#if defined(CONFIG_85xx) || defined(CONFIG_83xx)
+#if defined(CONFIG_85xx) || defined(CONFIG_83xx) || defined(CONFIG_MPC10X_BRIDGE)
 #include <asm/ppc_sys.h>
 #endif
 
@@ -61,8 +61,6 @@
 
 extern boot_infos_t *boot_infos;
 struct ide_machdep_calls ppc_ide_md;
-char *sysmap;
-unsigned long sysmap_size;
 
 /* Used with the BI_MEMSIZE bootinfo parameter to store the memory
    size value reported by the boot loader. */
@@ -249,7 +247,7 @@
 	seq_printf(m, "bogomips\t: %lu.%02lu\n",
 		   lpj / (500000/HZ), (lpj / (5000/HZ)) % 100);
 
-#if defined(CONFIG_85xx) || defined(CONFIG_83xx)
+#if defined(CONFIG_85xx) || defined(CONFIG_83xx) || defined(CONFIG_MPC10X_BRIDGE)
 	if (cur_ppc_sys_spec->ppc_sys_name)
 		seq_printf(m, "chipset\t\t: %s\n",
 			cur_ppc_sys_spec->ppc_sys_name);
@@ -578,11 +576,6 @@
 		case BI_CMD_LINE:
 			strlcpy(cmd_line, (void *)data, sizeof(cmd_line));
 			break;
-		case BI_SYSMAP:
-			sysmap = (char *)((data[0] >= (KERNELBASE)) ? data[0] :
-					  (data[0]+KERNELBASE));
-			sysmap_size = data[1];
-			break;
 #ifdef CONFIG_BLK_DEV_INITRD
 		case BI_INITRD:
 			initrd_start = data[0] + KERNELBASE;
diff --git a/arch/ppc/kernel/traps.c b/arch/ppc/kernel/traps.c
index c65731e..2ca8ecf 100644
--- a/arch/ppc/kernel/traps.c
+++ b/arch/ppc/kernel/traps.c
@@ -81,8 +81,10 @@
 	console_verbose();
 	spin_lock_irq(&die_lock);
 #ifdef CONFIG_PMAC_BACKLIGHT
-	set_backlight_enable(1);
-	set_backlight_level(BACKLIGHT_MAX);
+	if (_machine == _MACH_Pmac) {
+		set_backlight_enable(1);
+		set_backlight_level(BACKLIGHT_MAX);
+	}
 #endif
 	printk("Oops: %s, sig: %ld [#%d]\n", str, err, ++die_counter);
 #ifdef CONFIG_PREEMPT
diff --git a/arch/ppc/lib/locks.c b/arch/ppc/lib/locks.c
index 694163d..c450dc4 100644
--- a/arch/ppc/lib/locks.c
+++ b/arch/ppc/lib/locks.c
@@ -130,7 +130,7 @@
 		while (!read_can_lock(rw)) {
 			if (--stuck == 0) {
 				printk("_read_lock(%p) CPU#%d lock %d\n",
-				       rw, _smp_processor_id(), rw->lock);
+				       rw, raw_smp_processor_id(), rw->lock);
 				stuck = INIT_STUCK;
 			}
 		}
@@ -158,7 +158,7 @@
 		while (!write_can_lock(rw)) {
 			if (--stuck == 0) {
 				printk("write_lock(%p) CPU#%d lock %d)\n",
-				       rw, _smp_processor_id(), rw->lock);
+				       rw, raw_smp_processor_id(), rw->lock);
 				stuck = INIT_STUCK;
 			}
 		}
diff --git a/arch/ppc/mm/fsl_booke_mmu.c b/arch/ppc/mm/fsl_booke_mmu.c
index 36233bd..e07990e 100644
--- a/arch/ppc/mm/fsl_booke_mmu.c
+++ b/arch/ppc/mm/fsl_booke_mmu.c
@@ -64,6 +64,8 @@
 extern unsigned long __max_low_memory;
 #define MAX_LOW_MEM	CONFIG_LOWMEM_SIZE
 
+#define NUM_TLBCAMS	(16)
+
 struct tlbcam {
    	u32	MAS0;
 	u32	MAS1;
diff --git a/arch/ppc/mm/init.c b/arch/ppc/mm/init.c
index 363c157..334ef41 100644
--- a/arch/ppc/mm/init.c
+++ b/arch/ppc/mm/init.c
@@ -96,9 +96,6 @@
 char *klimit = _end;
 struct mem_pieces phys_avail;
 
-extern char *sysmap;
-extern unsigned long sysmap_size;
-
 /*
  * this tells the system to map all of ram with the segregs
  * (i.e. page tables) instead of the bats.
@@ -442,12 +439,6 @@
 	if (agp_special_page)
 		SetPageReserved(virt_to_page(agp_special_page));
 #endif
-	if ( sysmap )
-		for (addr = (unsigned long)sysmap;
-		     addr < PAGE_ALIGN((unsigned long)sysmap+sysmap_size) ;
-		     addr += PAGE_SIZE)
-			SetPageReserved(virt_to_page(addr));
-
 	for (addr = PAGE_OFFSET; addr < (unsigned long)high_memory;
 	     addr += PAGE_SIZE) {
 		if (!PageReserved(virt_to_page(addr)))
@@ -469,7 +460,6 @@
 			struct page *page = mem_map + pfn;
 
 			ClearPageReserved(page);
-			set_bit(PG_highmem, &page->flags);
 			set_page_count(page, 1);
 			__free_page(page);
 			totalhigh_pages++;
@@ -483,9 +473,7 @@
 	       codepages<< (PAGE_SHIFT-10), datapages<< (PAGE_SHIFT-10),
 	       initpages<< (PAGE_SHIFT-10),
 	       (unsigned long) (totalhigh_pages << (PAGE_SHIFT-10)));
-	if (sysmap)
-		printk("System.map loaded at 0x%08x for debugger, size: %ld bytes\n",
-			(unsigned int)sysmap, sysmap_size);
+
 #ifdef CONFIG_PPC_PMAC
 	if (agp_special_page)
 		printk(KERN_INFO "AGP special page: 0x%08lx\n", agp_special_page);
@@ -535,9 +523,6 @@
 	if (rtas_data)
 		mem_pieces_remove(&phys_avail, rtas_data, rtas_size, 1);
 #endif
-	/* remove the sysmap pages from the available memory */
-	if (sysmap)
-		mem_pieces_remove(&phys_avail, __pa(sysmap), sysmap_size, 1);
 #ifdef CONFIG_PPC_PMAC
 	/* Because of some uninorth weirdness, we need a page of
 	 * memory as high as possible (it must be outside of the
diff --git a/arch/ppc/mm/mmu_decl.h b/arch/ppc/mm/mmu_decl.h
index ffcdb46..540f329 100644
--- a/arch/ppc/mm/mmu_decl.h
+++ b/arch/ppc/mm/mmu_decl.h
@@ -43,6 +43,8 @@
 extern PTE *Hash, *Hash_end;
 extern unsigned long Hash_size, Hash_mask;
 
+extern unsigned int num_tlbcam_entries;
+
 /* ...and now those things that may be slightly different between processor
  * architectures.  -- Dan
  */
diff --git a/arch/ppc/mm/pgtable.c b/arch/ppc/mm/pgtable.c
index 5d2f3f6..81a3d74 100644
--- a/arch/ppc/mm/pgtable.c
+++ b/arch/ppc/mm/pgtable.c
@@ -66,7 +66,6 @@
 
 #ifdef HAVE_TLBCAM
 extern unsigned int tlbcam_index;
-extern unsigned int num_tlbcam_entries;
 extern unsigned long v_mapped_by_tlbcam(unsigned long va);
 extern unsigned long p_mapped_by_tlbcam(unsigned long pa);
 #else /* !HAVE_TLBCAM */
diff --git a/arch/ppc/platforms/83xx/mpc834x_sys.c b/arch/ppc/platforms/83xx/mpc834x_sys.c
index e6348b5..86ca5cf 100644
--- a/arch/ppc/platforms/83xx/mpc834x_sys.c
+++ b/arch/ppc/platforms/83xx/mpc834x_sys.c
@@ -41,7 +41,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/ipic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
diff --git a/arch/ppc/platforms/85xx/Kconfig b/arch/ppc/platforms/85xx/Kconfig
index ff92e38..c5bc282 100644
--- a/arch/ppc/platforms/85xx/Kconfig
+++ b/arch/ppc/platforms/85xx/Kconfig
@@ -21,6 +21,11 @@
 	help
 	  This option enables support for the MPC 8540 ADS evaluation board.
 
+config MPC8548_CDS
+	bool "Freescale MPC8548 CDS"
+	help
+	  This option enablese support for the MPC8548 CDS evaluation board.
+
 config MPC8555_CDS
 	bool "Freescale MPC8555 CDS"
 	help
@@ -53,6 +58,11 @@
 	depends on MPC8540_ADS
 	default y
 
+config MPC8548
+	bool
+	depends on MPC8548_CDS
+	default y
+
 config MPC8555
 	bool
 	depends on MPC8555_CDS
diff --git a/arch/ppc/platforms/85xx/Makefile b/arch/ppc/platforms/85xx/Makefile
index 854fbd2..efdf813 100644
--- a/arch/ppc/platforms/85xx/Makefile
+++ b/arch/ppc/platforms/85xx/Makefile
@@ -2,6 +2,7 @@
 # Makefile for the PowerPC 85xx linux kernel.
 #
 obj-$(CONFIG_MPC8540_ADS)	+= mpc85xx_ads_common.o mpc8540_ads.o
+obj-$(CONFIG_MPC8548_CDS)	+= mpc85xx_cds_common.o
 obj-$(CONFIG_MPC8555_CDS)	+= mpc85xx_cds_common.o
 obj-$(CONFIG_MPC8560_ADS)	+= mpc85xx_ads_common.o mpc8560_ads.o
 obj-$(CONFIG_SBC8560)		+= sbc85xx.o sbc8560.o
diff --git a/arch/ppc/platforms/85xx/mpc8540_ads.c b/arch/ppc/platforms/85xx/mpc8540_ads.c
index 583838a..a2ed611 100644
--- a/arch/ppc/platforms/85xx/mpc8540_ads.c
+++ b/arch/ppc/platforms/85xx/mpc8540_ads.c
@@ -41,7 +41,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
@@ -88,7 +87,7 @@
 #ifdef CONFIG_SERIAL_TEXT_DEBUG
 	/* Invalidate the entry we stole earlier the serial ports
 	 * should be properly mapped */
-	invalidate_tlbcam_entry(NUM_TLBCAMS - 1);
+	invalidate_tlbcam_entry(num_tlbcam_entries - 1);
 #endif
 
 	/* setup the board related information for the enet controllers */
@@ -150,7 +149,7 @@
 		struct uart_port p;
 
 		/* Use the last TLB entry to map CCSRBAR to allow access to DUART regs */
-		settlbcam(NUM_TLBCAMS - 1, binfo->bi_immr_base,
+		settlbcam(num_tlbcam_entries - 1, binfo->bi_immr_base,
 			  binfo->bi_immr_base, MPC85xx_CCSRBAR_SIZE, _PAGE_IO, 0);
 
 		memset(&p, 0, sizeof (p));
diff --git a/arch/ppc/platforms/85xx/mpc8560_ads.c b/arch/ppc/platforms/85xx/mpc8560_ads.c
index 761b8c7..d87dfd5 100644
--- a/arch/ppc/platforms/85xx/mpc8560_ads.c
+++ b/arch/ppc/platforms/85xx/mpc8560_ads.c
@@ -41,7 +41,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
diff --git a/arch/ppc/platforms/85xx/mpc85xx_ads_common.c b/arch/ppc/platforms/85xx/mpc85xx_ads_common.c
index ba9f9f5..18e952d 100644
--- a/arch/ppc/platforms/85xx/mpc85xx_ads_common.c
+++ b/arch/ppc/platforms/85xx/mpc85xx_ads_common.c
@@ -36,7 +36,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
@@ -59,40 +58,8 @@
 unsigned char __res[sizeof (bd_t)];
 
 /* Internal interrupts are all Level Sensitive, and Positive Polarity */
-
 static u_char mpc85xx_ads_openpic_initsenses[] __initdata = {
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  0: L2 Cache */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  1: ECM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  2: DDR DRAM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  3: LBIU */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  4: DMA 0 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  5: DMA 1 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  6: DMA 2 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  7: DMA 3 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  8: PCI/PCI-X */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  9: RIO Inbound Port Write Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 10: RIO Doorbell Inbound */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 11: RIO Outbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 12: RIO Inbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 13: TSEC 0 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 14: TSEC 0 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 15: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 16: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 17: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 18: TSEC 0 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 19: TSEC 1 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 20: TSEC 1 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 21: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 22: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 23: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 24: TSEC 1 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 25: Fast Ethernet */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 26: DUART */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 27: I2C */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 28: Performance Monitor */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 29: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 30: CPM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 31: Unused */
+	MPC85XX_INTERNAL_IRQ_SENSES,
 	0x0,						/* External  0: */
 #if defined(CONFIG_PCI)
 	(IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),	/* External 1: PCI slot 0 */
@@ -159,7 +126,7 @@
 	/* Skip reserved space and internal sources */
 	openpic_set_sources(0, 32, OpenPIC_Addr + 0x10200);
 	/* Map PIC IRQs 0-11 */
-	openpic_set_sources(32, 12, OpenPIC_Addr + 0x10000);
+	openpic_set_sources(48, 12, OpenPIC_Addr + 0x10000);
 
 	/* we let openpic interrupts starting from an offset, to
 	 * leave space for cascading interrupts underneath.
diff --git a/arch/ppc/platforms/85xx/mpc85xx_cds_common.c b/arch/ppc/platforms/85xx/mpc85xx_cds_common.c
index e7cfa49..203b2ca 100644
--- a/arch/ppc/platforms/85xx/mpc85xx_cds_common.c
+++ b/arch/ppc/platforms/85xx/mpc85xx_cds_common.c
@@ -42,7 +42,6 @@
 #include <asm/todc.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/i8259.h>
 #include <asm/bootinfo.h>
@@ -73,40 +72,8 @@
 static volatile u8 * cadmus;
 
 /* Internal interrupts are all Level Sensitive, and Positive Polarity */
-
 static u_char mpc85xx_cds_openpic_initsenses[] __initdata = {
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  0: L2 Cache */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  1: ECM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  2: DDR DRAM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  3: LBIU */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  4: DMA 0 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  5: DMA 1 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  6: DMA 2 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  7: DMA 3 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  8: PCI/PCI-X */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  9: RIO Inbound Port Write Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 10: RIO Doorbell Inbound */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 11: RIO Outbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 12: RIO Inbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 13: TSEC 0 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 14: TSEC 0 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 15: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 16: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 17: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 18: TSEC 0 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 19: TSEC 1 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 20: TSEC 1 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 21: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 22: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 23: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 24: TSEC 1 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 25: Fast Ethernet */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 26: DUART */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 27: I2C */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 28: Performance Monitor */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 29: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 30: CPM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 31: Unused */
+	MPC85XX_INTERNAL_IRQ_SENSES,
 #if defined(CONFIG_PCI)
 	(IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),	/* External 0: PCI1 slot */
 	(IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),	/* External 1: PCI1 slot */
@@ -182,7 +149,6 @@
 mpc85xx_cds_init_IRQ(void)
 {
 	bd_t *binfo = (bd_t *) __res;
-	int i;
 
 	/* Determine the Physical Address of the OpenPIC regs */
 	phys_addr_t OpenPIC_PAddr = binfo->bi_immr_base + MPC85xx_OPENPIC_OFFSET;
@@ -191,9 +157,13 @@
 	OpenPIC_NumInitSenses = sizeof (mpc85xx_cds_openpic_initsenses);
 
 	/* Skip reserved space and internal sources */
+#ifdef CONFIG_MPC8548
+	openpic_set_sources(0, 48, OpenPIC_Addr + 0x10200);
+#else
 	openpic_set_sources(0, 32, OpenPIC_Addr + 0x10200);
+#endif
 	/* Map PIC IRQs 0-11 */
-	openpic_set_sources(32, 12, OpenPIC_Addr + 0x10000);
+	openpic_set_sources(48, 12, OpenPIC_Addr + 0x10000);
 
 	/* we let openpic interrupts starting from an offset, to
 	 * leave space for cascading interrupts underneath.
@@ -475,26 +445,52 @@
 #ifdef CONFIG_SERIAL_TEXT_DEBUG
 	/* Invalidate the entry we stole earlier the serial ports
 	 * should be properly mapped */
-	invalidate_tlbcam_entry(NUM_TLBCAMS - 1);
+	invalidate_tlbcam_entry(num_tlbcam_entries - 1);
 #endif
 
 	/* setup the board related information for the enet controllers */
 	pdata = (struct gianfar_platform_data *) ppc_sys_get_pdata(MPC85xx_TSEC1);
-	pdata->board_flags = FSL_GIANFAR_BRD_HAS_PHY_INTR;
-	pdata->interruptPHY = MPC85xx_IRQ_EXT5;
-	pdata->phyid = 0;
-	/* fixup phy address */
-	pdata->phy_reg_addr += binfo->bi_immr_base;
-	memcpy(pdata->mac_addr, binfo->bi_enetaddr, 6);
+	if (pdata) {
+		pdata->board_flags = FSL_GIANFAR_BRD_HAS_PHY_INTR;
+		pdata->interruptPHY = MPC85xx_IRQ_EXT5;
+		pdata->phyid = 0;
+		/* fixup phy address */
+		pdata->phy_reg_addr += binfo->bi_immr_base;
+		memcpy(pdata->mac_addr, binfo->bi_enetaddr, 6);
+	}
 
 	pdata = (struct gianfar_platform_data *) ppc_sys_get_pdata(MPC85xx_TSEC2);
-	pdata->board_flags = FSL_GIANFAR_BRD_HAS_PHY_INTR;
-	pdata->interruptPHY = MPC85xx_IRQ_EXT5;
-	pdata->phyid = 1;
-	/* fixup phy address */
-	pdata->phy_reg_addr += binfo->bi_immr_base;
-	memcpy(pdata->mac_addr, binfo->bi_enet1addr, 6);
+	if (pdata) {
+		pdata->board_flags = FSL_GIANFAR_BRD_HAS_PHY_INTR;
+		pdata->interruptPHY = MPC85xx_IRQ_EXT5;
+		pdata->phyid = 1;
+		/* fixup phy address */
+		pdata->phy_reg_addr += binfo->bi_immr_base;
+		memcpy(pdata->mac_addr, binfo->bi_enet1addr, 6);
+	}
 
+	pdata = (struct gianfar_platform_data *) ppc_sys_get_pdata(MPC85xx_eTSEC1);
+	if (pdata) {
+		pdata->board_flags = FSL_GIANFAR_BRD_HAS_PHY_INTR;
+		pdata->interruptPHY = MPC85xx_IRQ_EXT5;
+		pdata->phyid = 0;
+		/* fixup phy address */
+		pdata->phy_reg_addr += binfo->bi_immr_base;
+		memcpy(pdata->mac_addr, binfo->bi_enetaddr, 6);
+	}
+
+	pdata = (struct gianfar_platform_data *) ppc_sys_get_pdata(MPC85xx_eTSEC2);
+	if (pdata) {
+		pdata->board_flags = FSL_GIANFAR_BRD_HAS_PHY_INTR;
+		pdata->interruptPHY = MPC85xx_IRQ_EXT5;
+		pdata->phyid = 1;
+		/* fixup phy address */
+		pdata->phy_reg_addr += binfo->bi_immr_base;
+		memcpy(pdata->mac_addr, binfo->bi_enet1addr, 6);
+	}
+
+	ppc_sys_device_remove(MPC85xx_eTSEC3);
+	ppc_sys_device_remove(MPC85xx_eTSEC4);
 
 #ifdef CONFIG_BLK_DEV_INITRD
 	if (initrd_start)
@@ -531,7 +527,7 @@
 		struct uart_port p;
 
 		/* Use the last TLB entry to map CCSRBAR to allow access to DUART regs */
-		settlbcam(NUM_TLBCAMS - 1, binfo->bi_immr_base,
+		settlbcam(num_tlbcam_entries - 1, binfo->bi_immr_base,
 				binfo->bi_immr_base, MPC85xx_CCSRBAR_SIZE, _PAGE_IO, 0);
 
 		memset(&p, 0, sizeof (p));
diff --git a/arch/ppc/platforms/85xx/sbc8560.c b/arch/ppc/platforms/85xx/sbc8560.c
index 7b9e154..3dbdd73 100644
--- a/arch/ppc/platforms/85xx/sbc8560.c
+++ b/arch/ppc/platforms/85xx/sbc8560.c
@@ -41,7 +41,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
@@ -125,7 +124,7 @@
 #ifdef CONFIG_SERIAL_TEXT_DEBUG
 	/* Invalidate the entry we stole earlier the serial ports
 	 * should be properly mapped */ 
-	invalidate_tlbcam_entry(NUM_TLBCAMS - 1);
+	invalidate_tlbcam_entry(num_tlbcam_entries - 1);
 #endif
 
 	/* setup the board related information for the enet controllers */
@@ -176,7 +175,7 @@
 
 #ifdef CONFIG_SERIAL_TEXT_DEBUG
 	/* Use the last TLB entry to map CCSRBAR to allow access to DUART regs */
-	settlbcam(NUM_TLBCAMS - 1, UARTA_ADDR,
+	settlbcam(num_tlbcam_entries - 1, UARTA_ADDR,
 		  UARTA_ADDR, 0x1000, _PAGE_IO, 0);
 #endif
 
diff --git a/arch/ppc/platforms/85xx/sbc85xx.c b/arch/ppc/platforms/85xx/sbc85xx.c
index 2d638c1..4f6d1dd 100644
--- a/arch/ppc/platforms/85xx/sbc85xx.c
+++ b/arch/ppc/platforms/85xx/sbc85xx.c
@@ -35,7 +35,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
@@ -59,40 +58,8 @@
 extern unsigned long total_memory;	/* in mm/init */
 
 /* Internal interrupts are all Level Sensitive, and Positive Polarity */
-
 static u_char sbc8560_openpic_initsenses[] __initdata = {
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  0: L2 Cache */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  1: ECM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  2: DDR DRAM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  3: LBIU */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  4: DMA 0 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  5: DMA 1 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  6: DMA 2 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  7: DMA 3 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  8: PCI/PCI-X */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  9: RIO Inbound Port Write Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 10: RIO Doorbell Inbound */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 11: RIO Outbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 12: RIO Inbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 13: TSEC 0 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 14: TSEC 0 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 15: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 16: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 17: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 18: TSEC 0 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 19: TSEC 1 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 20: TSEC 1 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 21: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 22: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 23: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 24: TSEC 1 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 25: Fast Ethernet */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 26: DUART */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 27: I2C */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 28: Performance Monitor */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 29: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 30: CPM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 31: Unused */
+	MPC85XX_INTERNAL_IRQ_SENSES,
 	0x0,				/* External  0: */
 	0x0,				/* External  1: */
 #if defined(CONFIG_PCI)
@@ -159,7 +126,7 @@
 	/* Skip reserved space and internal sources */
 	openpic_set_sources(0, 32, OpenPIC_Addr + 0x10200);
 	/* Map PIC IRQs 0-11 */
-	openpic_set_sources(32, 12, OpenPIC_Addr + 0x10000);
+	openpic_set_sources(48, 12, OpenPIC_Addr + 0x10000);
 
 	/* we let openpic interrupts starting from an offset, to 
 	 * leave space for cascading interrupts underneath.
diff --git a/arch/ppc/platforms/85xx/stx_gp3.c b/arch/ppc/platforms/85xx/stx_gp3.c
index bc95836..9455bb6 100644
--- a/arch/ppc/platforms/85xx/stx_gp3.c
+++ b/arch/ppc/platforms/85xx/stx_gp3.c
@@ -46,7 +46,6 @@
 #include <asm/time.h>
 #include <asm/io.h>
 #include <asm/machdep.h>
-#include <asm/prom.h>
 #include <asm/open_pic.h>
 #include <asm/bootinfo.h>
 #include <asm/pci-bridge.h>
@@ -72,38 +71,7 @@
 
 /* Internal interrupts are all Level Sensitive, and Positive Polarity */
 static u8 gp3_openpic_initsenses[] __initdata = {
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  0: L2 Cache */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  1: ECM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  2: DDR DRAM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  3: LBIU */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  4: DMA 0 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  5: DMA 1 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  6: DMA 2 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  7: DMA 3 */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  8: PCI/PCI-X */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  9: RIO Inbound Port Write Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 10: RIO Doorbell Inbound */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 11: RIO Outbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 12: RIO Inbound Message */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 13: TSEC 0 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 14: TSEC 0 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 15: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 16: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 17: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 18: TSEC 0 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 19: TSEC 1 Transmit */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 20: TSEC 1 Receive */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 21: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 22: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 23: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 24: TSEC 1 Receive/Transmit Error */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 25: Fast Ethernet */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 26: DUART */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 27: I2C */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 28: Performance Monitor */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 29: Unused */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 30: CPM */
-	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 31: Unused */
+	MPC85XX_INTERNAL_IRQ_SENSES,
 	0x0,						/* External  0: */
 #if defined(CONFIG_PCI)
 	(IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),	/* External 1: PCI slot 0 */
@@ -200,7 +168,6 @@
 static void __init
 gp3_init_IRQ(void)
 {
-	int i;
 	bd_t *binfo = (bd_t *) __res;
 
 	/*
@@ -218,7 +185,7 @@
 	openpic_set_sources(0, 32, OpenPIC_Addr + 0x10200);
 
 	/* Map PIC IRQs 0-11 */
-	openpic_set_sources(32, 12, OpenPIC_Addr + 0x10000);
+	openpic_set_sources(48, 12, OpenPIC_Addr + 0x10000);
 
 	/*
 	 * Let openpic interrupts starting from an offset, to
diff --git a/arch/ppc/platforms/sandpoint.c b/arch/ppc/platforms/sandpoint.c
index 531bfa0..70e58f4 100644
--- a/arch/ppc/platforms/sandpoint.c
+++ b/arch/ppc/platforms/sandpoint.c
@@ -81,6 +81,7 @@
 #include <linux/serial.h>
 #include <linux/tty.h>	/* for linux/serial_core.h */
 #include <linux/serial_core.h>
+#include <linux/serial_8250.h>
 
 #include <asm/system.h>
 #include <asm/pgtable.h>
@@ -99,6 +100,7 @@
 #include <asm/mpc10x.h>
 #include <asm/pci-bridge.h>
 #include <asm/kgdb.h>
+#include <asm/ppc_sys.h>
 
 #include "sandpoint.h"
 
@@ -305,6 +307,24 @@
 	/* Lookup PCI host bridges */
 	sandpoint_find_bridges();
 
+	if (strncmp (cur_ppc_sys_spec->ppc_sys_name, "8245", 4) == 0)
+	{
+		bd_t *bp = (bd_t *)__res;
+		struct plat_serial8250_port *pdata;
+		pdata = (struct plat_serial8250_port *) ppc_sys_get_pdata(MPC10X_DUART);
+
+		if (pdata)
+		{
+			pdata[0].uartclk = bp->bi_busfreq;
+			pdata[0].membase = ioremap(pdata[0].mapbase, 0x100);
+
+			/* this disables the 2nd serial port on the DUART
+			 * since the sandpoint does not have it connected */
+			pdata[1].uartclk = 0;
+			pdata[1].irq = 0;
+			pdata[1].mapbase = 0;
+		}
+
 	printk(KERN_INFO "Motorola SPS Sandpoint Test Platform\n");
 	printk(KERN_INFO "Port by MontaVista Software, Inc. (source@mvista.com)\n");
 
diff --git a/arch/ppc/syslib/Makefile b/arch/ppc/syslib/Makefile
index 96acf85..dec5bf4 100644
--- a/arch/ppc/syslib/Makefile
+++ b/arch/ppc/syslib/Makefile
@@ -92,7 +92,7 @@
 obj-$(CONFIG_SERIAL_TEXT_DEBUG)	+= mv64x60_dbg.o
 endif
 obj-$(CONFIG_BOOTX_TEXT)	+= btext.o
-obj-$(CONFIG_MPC10X_BRIDGE)     += mpc10x_common.o indirect_pci.o
+obj-$(CONFIG_MPC10X_BRIDGE)	+= mpc10x_common.o indirect_pci.o ppc_sys.o
 obj-$(CONFIG_MPC10X_OPENPIC)	+= open_pic.o
 obj-$(CONFIG_40x)		+= dcr.o
 obj-$(CONFIG_BOOKE)		+= dcr.o
@@ -107,6 +107,7 @@
 ifeq ($(CONFIG_83xx),y)
 obj-$(CONFIG_PCI)		+= indirect_pci.o pci_auto.o
 endif
+obj-$(CONFIG_MPC8548_CDS)	+= todc_time.o
 obj-$(CONFIG_MPC8555_CDS)	+= todc_time.o
 obj-$(CONFIG_PPC_MPC52xx)	+= mpc52xx_setup.o mpc52xx_pic.o \
 					mpc52xx_sys.o mpc52xx_devices.o ppc_sys.o
diff --git a/arch/ppc/syslib/mpc10x_common.c b/arch/ppc/syslib/mpc10x_common.c
index fd93adf..8fc5f41 100644
--- a/arch/ppc/syslib/mpc10x_common.c
+++ b/arch/ppc/syslib/mpc10x_common.c
@@ -21,6 +21,9 @@
 #include <linux/init.h>
 #include <linux/pci.h>
 #include <linux/slab.h>
+#include <linux/serial_8250.h>
+#include <linux/fsl_devices.h>
+#include <linux/device.h>
 
 #include <asm/byteorder.h>
 #include <asm/io.h>
@@ -30,16 +33,7 @@
 #include <asm/pci-bridge.h>
 #include <asm/open_pic.h>
 #include <asm/mpc10x.h>
-#include <asm/ocp.h>
-
-/* The OCP structure is fixed by code below, before OCP initialises.
-   paddr depends on where the board places the EUMB.
-    - fixed in mpc10x_bridge_init().
-   irq depends on two things:
-    > does the board use the EPIC at all? (PCORE does not).
-    > is the EPIC in serial or parallel mode?
-    - fixed in mpc10x_set_openpic().
-*/
+#include <asm/ppc_sys.h>
 
 #ifdef CONFIG_MPC10X_OPENPIC
 #ifdef CONFIG_EPIC_SERIAL_MODE
@@ -50,35 +44,140 @@
 #define MPC10X_I2C_IRQ (EPIC_IRQ_BASE + NUM_8259_INTERRUPTS)
 #define MPC10X_DMA0_IRQ (EPIC_IRQ_BASE + 1 + NUM_8259_INTERRUPTS)
 #define MPC10X_DMA1_IRQ (EPIC_IRQ_BASE + 2 + NUM_8259_INTERRUPTS)
+#define MPC10X_UART0_IRQ (EPIC_IRQ_BASE + 4 + NUM_8259_INTERRUPTS)
 #else
-#define MPC10X_I2C_IRQ OCP_IRQ_NA
-#define MPC10X_DMA0_IRQ OCP_IRQ_NA
-#define MPC10X_DMA1_IRQ OCP_IRQ_NA
+#define MPC10X_I2C_IRQ -1
+#define MPC10X_DMA0_IRQ -1
+#define MPC10X_DMA1_IRQ -1
+#define MPC10X_UART0_IRQ -1
 #endif
 
-
-struct ocp_def core_ocp[] = {
-	{ .vendor	= OCP_VENDOR_INVALID
-	}
+static struct fsl_i2c_platform_data mpc10x_i2c_pdata = {
+	.device_flags		= 0,
 };
 
-static struct ocp_fs_i2c_data mpc10x_i2c_data = {
-	.flags		= 0
-};
-static struct ocp_def mpc10x_i2c_ocp = {
-	.vendor		= OCP_VENDOR_MOTOROLA,
-	.function	= OCP_FUNC_IIC,
-	.index		= 0,
-	.additions	= &mpc10x_i2c_data
+static struct plat_serial8250_port serial_platform_data[] = {
+	[0] = {
+		.mapbase	= 0x4500,
+		.iotype		= UPIO_MEM,
+		.flags		= UPF_BOOT_AUTOCONF | UPF_SKIP_TEST,
+	},
+	[1] = {
+		.mapbase	= 0x4600,
+		.iotype		= UPIO_MEM,
+		.flags		= UPF_BOOT_AUTOCONF | UPF_SKIP_TEST,
+	},
+	{ },
 };
 
-static struct ocp_def mpc10x_dma_ocp[2] = {
-{	.vendor		= OCP_VENDOR_MOTOROLA,
-	.function	= OCP_FUNC_DMA,
-	.index		= 0 },
-{	.vendor		= OCP_VENDOR_MOTOROLA,
-	.function	= OCP_FUNC_DMA,
-	.index		= 1 }
+struct platform_device ppc_sys_platform_devices[] = {
+	[MPC10X_IIC1] = {
+		.name 	= "fsl-i2c",
+		.id	= 1,
+		.dev.platform_data = &mpc10x_i2c_pdata,
+		.num_resources = 2,
+		.resource = (struct resource[]) {
+			{
+				.start 	= MPC10X_EUMB_I2C_OFFSET,
+				.end	= MPC10X_EUMB_I2C_OFFSET +
+		                            MPC10X_EUMB_I2C_SIZE - 1,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.flags 	= IORESOURCE_IRQ
+			},
+		},
+	},
+	[MPC10X_DMA0] = {
+		.name	= "fsl-dma",
+		.id	= 0,
+		.num_resources = 2,
+		.resource = (struct resource[]) {
+			{
+				.start 	= MPC10X_EUMB_DMA_OFFSET + 0x10,
+				.end	= MPC10X_EUMB_DMA_OFFSET + 0x1f,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC10X_DMA1] = {
+		.name	= "fsl-dma",
+		.id	= 1,
+		.num_resources = 2,
+		.resource = (struct resource[]) {
+			{
+				.start	= MPC10X_EUMB_DMA_OFFSET + 0x20,
+				.end	= MPC10X_EUMB_DMA_OFFSET + 0x2f,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC10X_DMA1] = {
+		.name	= "fsl-dma",
+		.id	= 1,
+		.num_resources = 2,
+		.resource = (struct resource[]) {
+			{
+				.start	= MPC10X_EUMB_DMA_OFFSET + 0x20,
+				.end	= MPC10X_EUMB_DMA_OFFSET + 0x2f,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC10X_DUART] = {
+		.name = "serial8250",
+		.id	= 0,
+		.dev.platform_data = serial_platform_data,
+	},
+};
+
+/* We use the PCI ID to match on */
+struct ppc_sys_spec *cur_ppc_sys_spec;
+struct ppc_sys_spec ppc_sys_specs[] = {
+	{
+		.ppc_sys_name 	= "8245",
+		.mask		= 0xFFFFFFFF,
+		.value		= MPC10X_BRIDGE_8245,
+		.num_devices	= 4,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC10X_IIC1, MPC10X_DMA0, MPC10X_DMA1, MPC10X_DUART,
+		},
+	},
+	{
+		.ppc_sys_name 	= "8240",
+		.mask		= 0xFFFFFFFF,
+		.value		= MPC10X_BRIDGE_8240,
+		.num_devices	= 3,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC10X_IIC1, MPC10X_DMA0, MPC10X_DMA1,
+		},
+	},
+	{
+		.ppc_sys_name	= "107",
+		.mask		= 0xFFFFFFFF,
+		.value		= MPC10X_BRIDGE_107,
+		.num_devices	= 3,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC10X_IIC1, MPC10X_DMA0, MPC10X_DMA1,
+		},
+	},
+	{       /* default match */
+		.ppc_sys_name   = "",
+		.mask           = 0x00000000,
+		.value          = 0x00000000,
+	},
 };
 
 /* Set resources to match bridge memory map */
@@ -132,7 +231,7 @@
 		   uint new_map,
 		   uint phys_eumb_base)
 {
-	int	host_bridge, picr1, picr1_bit;
+	int	host_bridge, picr1, picr1_bit, i;
 	ulong	pci_config_addr, pci_config_data;
 	u_char	pir, byte;
 
@@ -273,7 +372,7 @@
 			printk("Host bridge in Agent mode\n");
 			/* Read or Set LMBAR & PCSRBAR? */
 		}
-		
+
 		/* Set base addr of the 8240/107 EUMB.  */
 		early_write_config_dword(hose,
 					 0,
@@ -287,17 +386,6 @@
 			ioremap(phys_eumb_base + MPC10X_EUMB_EPIC_OFFSET,
 				MPC10X_EUMB_EPIC_SIZE);
 #endif
-		mpc10x_i2c_ocp.paddr = phys_eumb_base + MPC10X_EUMB_I2C_OFFSET;
-		mpc10x_i2c_ocp.irq = MPC10X_I2C_IRQ;
-		ocp_add_one_device(&mpc10x_i2c_ocp);
-		mpc10x_dma_ocp[0].paddr = phys_eumb_base +
-					MPC10X_EUMB_DMA_OFFSET + 0x100;
-		mpc10x_dma_ocp[0].irq = MPC10X_DMA0_IRQ;
-		ocp_add_one_device(&mpc10x_dma_ocp[0]);
-		mpc10x_dma_ocp[1].paddr = phys_eumb_base +
-					MPC10X_EUMB_DMA_OFFSET + 0x200;
-		mpc10x_dma_ocp[1].irq = MPC10X_DMA1_IRQ;
-		ocp_add_one_device(&mpc10x_dma_ocp[1]);
 	}
 
 #ifdef CONFIG_MPC10X_STORE_GATHERING
@@ -306,6 +394,29 @@
 	mpc10x_disable_store_gathering(hose);
 #endif
 
+	/* setup platform devices for MPC10x bridges */
+	identify_ppc_sys_by_id (host_bridge);
+
+	for (i = 0; i < cur_ppc_sys_spec->num_devices; i++) {
+		unsigned int dev_id = cur_ppc_sys_spec->device_list[i];
+		ppc_sys_fixup_mem_resource(&ppc_sys_platform_devices[dev_id],
+			phys_eumb_base);
+	}
+
+	/* IRQ's are determined at runtime */
+	ppc_sys_platform_devices[MPC10X_IIC1].resource[1].start = MPC10X_I2C_IRQ;
+	ppc_sys_platform_devices[MPC10X_IIC1].resource[1].end = MPC10X_I2C_IRQ;
+	ppc_sys_platform_devices[MPC10X_DMA0].resource[1].start = MPC10X_DMA0_IRQ;
+	ppc_sys_platform_devices[MPC10X_DMA0].resource[1].end = MPC10X_DMA0_IRQ;
+	ppc_sys_platform_devices[MPC10X_DMA1].resource[1].start = MPC10X_DMA1_IRQ;
+	ppc_sys_platform_devices[MPC10X_DMA1].resource[1].end = MPC10X_DMA1_IRQ;
+
+	serial_platform_data[0].mapbase += phys_eumb_base;
+	serial_platform_data[0].irq = MPC10X_UART0_IRQ;
+
+	serial_platform_data[1].mapbase += phys_eumb_base;
+	serial_platform_data[1].irq = MPC10X_UART0_IRQ + 1;
+
 	/*
 	 * 8240 erratum 26, 8241/8245 erratum 29, 107 erratum 23: speculative
 	 * PCI reads may return stale data so turn off.
@@ -330,7 +441,7 @@
 	 * 8245 (Rev 2., dated 10/2003) says PICR2[0] is reserverd.
 	 */
 	if (host_bridge == MPC10X_BRIDGE_8245) {
-		ulong	picr2;
+		u32	picr2;
 
 		early_read_config_dword(hose, 0, PCI_DEVFN(0,0),
 			MPC10X_CFG_PICR2_REG, &picr2);
@@ -504,6 +615,8 @@
 	openpic_set_sources(EPIC_IRQ_BASE, 3, OpenPIC_Addr + 0x11020);
 	/* Skip reserved space and map Message Unit Interrupt (I2O) */
 	openpic_set_sources(EPIC_IRQ_BASE + 3, 1, OpenPIC_Addr + 0x110C0);
+	/* Skip reserved space and map Serial Interupts */
+	openpic_set_sources(EPIC_IRQ_BASE + 4, 2, OpenPIC_Addr + 0x11120);
 
 	openpic_init(NUM_8259_INTERRUPTS);
 }
diff --git a/arch/ppc/syslib/mpc85xx_devices.c b/arch/ppc/syslib/mpc85xx_devices.c
index 1e658ef..8af322d 100644
--- a/arch/ppc/syslib/mpc85xx_devices.c
+++ b/arch/ppc/syslib/mpc85xx_devices.c
@@ -40,6 +40,42 @@
 	.phy_reg_addr = MPC85xx_ENET1_OFFSET,
 };
 
+static struct gianfar_platform_data mpc85xx_etsec1_pdata = {
+	.device_flags = FSL_GIANFAR_DEV_HAS_GIGABIT |
+	    FSL_GIANFAR_DEV_HAS_COALESCE | FSL_GIANFAR_DEV_HAS_RMON |
+	    FSL_GIANFAR_DEV_HAS_MULTI_INTR |
+	    FSL_GIANFAR_DEV_HAS_CSUM | FSL_GIANFAR_DEV_HAS_VLAN |
+	    FSL_GIANFAR_DEV_HAS_EXTENDED_HASH,
+	.phy_reg_addr = MPC85xx_ENET1_OFFSET,
+};
+
+static struct gianfar_platform_data mpc85xx_etsec2_pdata = {
+	.device_flags = FSL_GIANFAR_DEV_HAS_GIGABIT |
+	    FSL_GIANFAR_DEV_HAS_COALESCE | FSL_GIANFAR_DEV_HAS_RMON |
+	    FSL_GIANFAR_DEV_HAS_MULTI_INTR |
+	    FSL_GIANFAR_DEV_HAS_CSUM | FSL_GIANFAR_DEV_HAS_VLAN |
+	    FSL_GIANFAR_DEV_HAS_EXTENDED_HASH,
+	.phy_reg_addr = MPC85xx_ENET1_OFFSET,
+};
+
+static struct gianfar_platform_data mpc85xx_etsec3_pdata = {
+	.device_flags = FSL_GIANFAR_DEV_HAS_GIGABIT |
+	    FSL_GIANFAR_DEV_HAS_COALESCE | FSL_GIANFAR_DEV_HAS_RMON |
+	    FSL_GIANFAR_DEV_HAS_MULTI_INTR |
+	    FSL_GIANFAR_DEV_HAS_CSUM | FSL_GIANFAR_DEV_HAS_VLAN |
+	    FSL_GIANFAR_DEV_HAS_EXTENDED_HASH,
+	.phy_reg_addr = MPC85xx_ENET1_OFFSET,
+};
+
+static struct gianfar_platform_data mpc85xx_etsec4_pdata = {
+	.device_flags = FSL_GIANFAR_DEV_HAS_GIGABIT |
+	    FSL_GIANFAR_DEV_HAS_COALESCE | FSL_GIANFAR_DEV_HAS_RMON |
+	    FSL_GIANFAR_DEV_HAS_MULTI_INTR |
+	    FSL_GIANFAR_DEV_HAS_CSUM | FSL_GIANFAR_DEV_HAS_VLAN |
+	    FSL_GIANFAR_DEV_HAS_EXTENDED_HASH,
+	.phy_reg_addr = MPC85xx_ENET1_OFFSET,
+};
+
 static struct gianfar_platform_data mpc85xx_fec_pdata = {
 	.phy_reg_addr = MPC85xx_ENET1_OFFSET,
 };
@@ -48,6 +84,10 @@
 	.device_flags = FSL_I2C_DEV_SEPARATE_DFSRR,
 };
 
+static struct fsl_i2c_platform_data mpc85xx_fsl_i2c2_pdata = {
+	.device_flags = FSL_I2C_DEV_SEPARATE_DFSRR,
+};
+
 static struct plat_serial8250_port serial_platform_data[] = {
 	[0] = {
 		.mapbase	= 0x4500,
@@ -281,7 +321,6 @@
 			},
 		},
 	},
-#ifdef CONFIG_CPM2
 	[MPC85xx_CPM_FCC1] = {
 		.name = "fsl-cpm-fcc",
 		.id	= 1,
@@ -535,7 +574,151 @@
 			},
 		},
 	},
-#endif /* CONFIG_CPM2 */
+	[MPC85xx_eTSEC1] = {
+		.name = "fsl-gianfar",
+		.id	= 1,
+		.dev.platform_data = &mpc85xx_etsec1_pdata,
+		.num_resources	 = 4,
+		.resource = (struct resource[]) {
+			{
+				.start	= MPC85xx_ENET1_OFFSET,
+				.end	= MPC85xx_ENET1_OFFSET +
+						MPC85xx_ENET1_SIZE - 1,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.name	= "tx",
+				.start	= MPC85xx_IRQ_TSEC1_TX,
+				.end	= MPC85xx_IRQ_TSEC1_TX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "rx",
+				.start	= MPC85xx_IRQ_TSEC1_RX,
+				.end	= MPC85xx_IRQ_TSEC1_RX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "error",
+				.start	= MPC85xx_IRQ_TSEC1_ERROR,
+				.end	= MPC85xx_IRQ_TSEC1_ERROR,
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC85xx_eTSEC2] = {
+		.name = "fsl-gianfar",
+		.id	= 2,
+		.dev.platform_data = &mpc85xx_etsec2_pdata,
+		.num_resources	 = 4,
+		.resource = (struct resource[]) {
+			{
+				.start	= MPC85xx_ENET2_OFFSET,
+				.end	= MPC85xx_ENET2_OFFSET +
+						MPC85xx_ENET2_SIZE - 1,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.name	= "tx",
+				.start	= MPC85xx_IRQ_TSEC2_TX,
+				.end	= MPC85xx_IRQ_TSEC2_TX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "rx",
+				.start	= MPC85xx_IRQ_TSEC2_RX,
+				.end	= MPC85xx_IRQ_TSEC2_RX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "error",
+				.start	= MPC85xx_IRQ_TSEC2_ERROR,
+				.end	= MPC85xx_IRQ_TSEC2_ERROR,
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC85xx_eTSEC3] = {
+		.name = "fsl-gianfar",
+		.id	= 3,
+		.dev.platform_data = &mpc85xx_etsec3_pdata,
+		.num_resources	 = 4,
+		.resource = (struct resource[]) {
+			{
+				.start	= MPC85xx_ENET3_OFFSET,
+				.end	= MPC85xx_ENET3_OFFSET +
+						MPC85xx_ENET3_SIZE - 1,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.name	= "tx",
+				.start	= MPC85xx_IRQ_TSEC3_TX,
+				.end	= MPC85xx_IRQ_TSEC3_TX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "rx",
+				.start	= MPC85xx_IRQ_TSEC3_RX,
+				.end	= MPC85xx_IRQ_TSEC3_RX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "error",
+				.start	= MPC85xx_IRQ_TSEC3_ERROR,
+				.end	= MPC85xx_IRQ_TSEC3_ERROR,
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC85xx_eTSEC4] = {
+		.name = "fsl-gianfar",
+		.id	= 4,
+		.dev.platform_data = &mpc85xx_etsec4_pdata,
+		.num_resources	 = 4,
+		.resource = (struct resource[]) {
+			{
+				.start	= 0x27000,
+				.end	= 0x27fff,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.name	= "tx",
+				.start	= MPC85xx_IRQ_TSEC4_TX,
+				.end	= MPC85xx_IRQ_TSEC4_TX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "rx",
+				.start	= MPC85xx_IRQ_TSEC4_RX,
+				.end	= MPC85xx_IRQ_TSEC4_RX,
+				.flags	= IORESOURCE_IRQ,
+			},
+			{
+				.name	= "error",
+				.start	= MPC85xx_IRQ_TSEC4_ERROR,
+				.end	= MPC85xx_IRQ_TSEC4_ERROR,
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
+	[MPC85xx_IIC2] = {
+		.name = "fsl-i2c",
+		.id	= 2,
+		.dev.platform_data = &mpc85xx_fsl_i2c2_pdata,
+		.num_resources	 = 2,
+		.resource = (struct resource[]) {
+			{
+				.start	= 0x03100,
+				.end	= 0x031ff,
+				.flags	= IORESOURCE_MEM,
+			},
+			{
+				.start	= MPC85xx_IRQ_IIC1,
+				.end	= MPC85xx_IRQ_IIC1,
+				.flags	= IORESOURCE_IRQ,
+			},
+		},
+	},
 };
 
 static int __init mach_mpc85xx_fixup(struct platform_device *pdev)
diff --git a/arch/ppc/syslib/mpc85xx_sys.c b/arch/ppc/syslib/mpc85xx_sys.c
index d806a92..6e3184a 100644
--- a/arch/ppc/syslib/mpc85xx_sys.c
+++ b/arch/ppc/syslib/mpc85xx_sys.c
@@ -110,6 +110,111 @@
 			MPC85xx_CPM_USB,
 		},
 	},
+	/* SVRs on 8548 rev1.0 matches for 8548/8547/8545 */
+	{
+		.ppc_sys_name	= "8548E",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80390010,
+		.num_devices	= 13,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2, MPC85xx_eTSEC3,
+			MPC85xx_eTSEC4, MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART, MPC85xx_SEC2,
+		},
+	},
+	{
+		.ppc_sys_name	= "8548",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80310010,
+		.num_devices	= 12,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2, MPC85xx_eTSEC3,
+			MPC85xx_eTSEC4, MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART,
+		},
+	},
+	{
+		.ppc_sys_name	= "8547E",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80390010,
+		.num_devices	= 13,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2, MPC85xx_eTSEC3,
+			MPC85xx_eTSEC4, MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART, MPC85xx_SEC2,
+		},
+	},
+	{
+		.ppc_sys_name	= "8547",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80310010,
+		.num_devices	= 12,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2, MPC85xx_eTSEC3,
+			MPC85xx_eTSEC4, MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART,
+		},
+	},
+	{
+		.ppc_sys_name	= "8545E",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80390010,
+		.num_devices	= 11,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2,
+			MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART, MPC85xx_SEC2,
+		},
+	},
+	{
+		.ppc_sys_name	= "8545",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80310010,
+		.num_devices	= 10,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2,
+			MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART,
+		},
+	},
+	{
+		.ppc_sys_name	= "8543E",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x803A0010,
+		.num_devices	= 11,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2,
+			MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART, MPC85xx_SEC2,
+		},
+	},
+	{
+		.ppc_sys_name	= "8543",
+		.mask 		= 0xFFFF00F0,
+		.value 		= 0x80320010,
+		.num_devices	= 10,
+		.device_list	= (enum ppc_sys_devices[])
+		{
+			MPC85xx_eTSEC1, MPC85xx_eTSEC2,
+			MPC85xx_IIC1, MPC85xx_IIC2,
+			MPC85xx_DMA0, MPC85xx_DMA1, MPC85xx_DMA2, MPC85xx_DMA3,
+			MPC85xx_PERFMON, MPC85xx_DUART,
+		},
+	},
 	{	/* default match */
 		.ppc_sys_name	= "",
 		.mask 		= 0x00000000,
diff --git a/arch/ppc/syslib/open_pic.c b/arch/ppc/syslib/open_pic.c
index 000ba47..b45d826 100644
--- a/arch/ppc/syslib/open_pic.c
+++ b/arch/ppc/syslib/open_pic.c
@@ -21,7 +21,6 @@
 #include <asm/signal.h>
 #include <asm/io.h>
 #include <asm/irq.h>
-#include <asm/prom.h>
 #include <asm/sections.h>
 #include <asm/open_pic.h>
 #include <asm/i8259.h>
diff --git a/arch/ppc/syslib/open_pic2.c b/arch/ppc/syslib/open_pic2.c
index ea26da0..7e272c5 100644
--- a/arch/ppc/syslib/open_pic2.c
+++ b/arch/ppc/syslib/open_pic2.c
@@ -25,7 +25,6 @@
 #include <asm/signal.h>
 #include <asm/io.h>
 #include <asm/irq.h>
-#include <asm/prom.h>
 #include <asm/sections.h>
 #include <asm/open_pic.h>
 #include <asm/i8259.h>
diff --git a/arch/ppc/syslib/ppc4xx_kgdb.c b/arch/ppc/syslib/ppc4xx_kgdb.c
deleted file mode 100644
index fe8668b..0000000
--- a/arch/ppc/syslib/ppc4xx_kgdb.c
+++ /dev/null
@@ -1,124 +0,0 @@
-#include <linux/config.h>
-#include <linux/types.h>
-#include <asm/ibm4xx.h>
-#include <linux/kernel.h>
-
-
-
-#define LSR_DR		0x01 /* Data ready */
-#define LSR_OE		0x02 /* Overrun */
-#define LSR_PE		0x04 /* Parity error */
-#define LSR_FE		0x08 /* Framing error */
-#define LSR_BI		0x10 /* Break */
-#define LSR_THRE	0x20 /* Xmit holding register empty */
-#define LSR_TEMT	0x40 /* Xmitter empty */
-#define LSR_ERR		0x80 /* Error */
-
-#include <platforms/4xx/ibm_ocp.h>
-
-extern struct NS16550* COM_PORTS[];
-#ifndef NULL
-#define NULL 0x00
-#endif
-
-static volatile struct NS16550 *kgdb_debugport = NULL;
-
-volatile struct NS16550 *
-NS16550_init(int chan)
-{
-	volatile struct NS16550 *com_port;
-	int quot;
-#ifdef BASE_BAUD
-	quot = BASE_BAUD / 9600;
-#else
-	quot = 0x000c; /* 0xc = 9600 baud (on a pc) */
-#endif
-
-	com_port = (struct NS16550 *) COM_PORTS[chan];
-
-	com_port->lcr = 0x00;
-	com_port->ier = 0xFF;
-	com_port->ier = 0x00;
-	com_port->lcr = com_port->lcr | 0x80; /* Access baud rate */
-	com_port->dll = ( quot & 0x00ff ); /* 0xc = 9600 baud */
-	com_port->dlm = ( quot & 0xff00 ) >> 8;
-	com_port->lcr = 0x03; /* 8 data, 1 stop, no parity */
-	com_port->mcr = 0x00; /* RTS/DTR */
-	com_port->fcr = 0x07; /* Clear & enable FIFOs */
-
-	return( com_port );
-}
-
-
-void
-NS16550_putc(volatile struct NS16550 *com_port, unsigned char c)
-{
-	while ((com_port->lsr & LSR_THRE) == 0)
-		;
-	com_port->thr = c;
-	return;
-}
-
-unsigned char
-NS16550_getc(volatile struct NS16550 *com_port)
-{
-	while ((com_port->lsr & LSR_DR) == 0)
-		;
-	return (com_port->rbr);
-}
-
-unsigned char
-NS16550_tstc(volatile struct NS16550 *com_port)
-{
-	return ((com_port->lsr & LSR_DR) != 0);
-}
-
-
-#if defined(CONFIG_KGDB_TTYS0)
-#define KGDB_PORT 0
-#elif defined(CONFIG_KGDB_TTYS1)
-#define KGDB_PORT 1
-#elif defined(CONFIG_KGDB_TTYS2)
-#define KGDB_PORT 2
-#elif defined(CONFIG_KGDB_TTYS3)
-#define KGDB_PORT 3
-#else
-#error "invalid kgdb_tty port"
-#endif
-
-void putDebugChar( unsigned char c )
-{
-	if ( kgdb_debugport == NULL )
-		kgdb_debugport = NS16550_init(KGDB_PORT);
-	NS16550_putc( kgdb_debugport, c );
-}
-
-int getDebugChar( void )
-{
-	if (kgdb_debugport == NULL)
-		kgdb_debugport = NS16550_init(KGDB_PORT);
-
-	return(NS16550_getc(kgdb_debugport));
-}
-
-void kgdb_interruptible(int enable)
-{
-	return;
-}
-
-void putDebugString(char* str)
-{
-	while (*str != '\0') {
-		putDebugChar(*str);
-		str++;
-	}
-	putDebugChar('\r');
-	return;
-}
-
-void
-kgdb_map_scc(void)
-{
-	printk("kgdb init \n");
-	kgdb_debugport = NS16550_init(KGDB_PORT);
-}
diff --git a/arch/ppc/syslib/ppc83xx_setup.c b/arch/ppc/syslib/ppc83xx_setup.c
index 843cf88..602a868 100644
--- a/arch/ppc/syslib/ppc83xx_setup.c
+++ b/arch/ppc/syslib/ppc83xx_setup.c
@@ -23,7 +23,6 @@
 #include <linux/serial_core.h>
 #include <linux/serial_8250.h>
 
-#include <asm/prom.h>
 #include <asm/time.h>
 #include <asm/mpc83xx.h>
 #include <asm/mmu.h>
diff --git a/arch/ppc/syslib/ppc85xx_setup.c b/arch/ppc/syslib/ppc85xx_setup.c
index f3277f4..ca95d79 100644
--- a/arch/ppc/syslib/ppc85xx_setup.c
+++ b/arch/ppc/syslib/ppc85xx_setup.c
@@ -23,7 +23,6 @@
 #include <linux/serial_core.h>
 #include <linux/serial_8250.h>
 
-#include <asm/prom.h>
 #include <asm/time.h>
 #include <asm/mpc85xx.h>
 #include <asm/immap_85xx.h>
@@ -33,6 +32,8 @@
 
 #include <syslib/ppc85xx_setup.h>
 
+extern void abort(void);
+
 /* Return the amount of memory */
 unsigned long __init
 mpc85xx_find_end_of_memory(void)
@@ -133,7 +134,7 @@
 
 #ifdef CONFIG_PCI
 
-#if defined(CONFIG_MPC8555_CDS)
+#if defined(CONFIG_MPC8555_CDS) || defined(CONFIG_MPC8548_CDS)
 extern void mpc85xx_cds_enable_via(struct pci_controller *hose);
 extern void mpc85xx_cds_fixup_via(struct pci_controller *hose);
 #endif
@@ -308,14 +309,14 @@
 
 	ppc_md.pci_exclude_device = mpc85xx_exclude_device;
 
-#if defined(CONFIG_MPC8555_CDS)
+#if defined(CONFIG_MPC8555_CDS) || defined(CONFIG_MPC8548_CDS)
 	/* Pre pciauto_bus_scan VIA init */
 	mpc85xx_cds_enable_via(hose_a);
 #endif
 
 	hose_a->last_busno = pciauto_bus_scan(hose_a, hose_a->first_busno);
 
-#if defined(CONFIG_MPC8555_CDS)
+#if defined(CONFIG_MPC8555_CDS) || defined(CONFIG_MPC8548_CDS)
 	/* Post pciauto_bus_scan VIA fixup */
 	mpc85xx_cds_fixup_via(hose_a);
 #endif
diff --git a/arch/ppc/xmon/xmon.c b/arch/ppc/xmon/xmon.c
index 8565f49..be7869e 100644
--- a/arch/ppc/xmon/xmon.c
+++ b/arch/ppc/xmon/xmon.c
@@ -9,6 +9,7 @@
 #include <linux/smp.h>
 #include <linux/interrupt.h>
 #include <linux/bitops.h>
+#include <linux/kallsyms.h>
 #include <asm/ptrace.h>
 #include <asm/string.h>
 #include <asm/prom.h>
@@ -93,8 +94,7 @@
 static unsigned read_spr(int);
 static void write_spr(int, unsigned);
 static void super_regs(void);
-static void print_sysmap(void);
-static void sysmap_lookup(void);
+static void symbol_lookup(void);
 static void remove_bpts(void);
 static void insert_bpts(void);
 static struct bpt *at_breakpoint(unsigned pc);
@@ -103,7 +103,6 @@
 #ifdef CONFIG_SMP
 static void cpu_cmd(void);
 #endif /* CONFIG_SMP */
-static int pretty_print_addr(unsigned long addr);
 static void csum(void);
 #ifdef CONFIG_BOOTX_TEXT
 static void vidcmds(void);
@@ -120,8 +119,6 @@
 
 extern void xmon_enter(void);
 extern void xmon_leave(void);
-extern char* xmon_find_symbol(unsigned long addr, unsigned long* saddr);
-extern unsigned long xmon_symbol_to_addr(char* symbol);
 
 static unsigned start_tb[NR_CPUS][2];
 static unsigned stop_tb[NR_CPUS][2];
@@ -148,7 +145,6 @@
   mm	move a block of memory\n\
   ms	set a block of memory\n\
   md	compare two blocks of memory\n\
-  M	print System.map\n\
   r	print registers\n\
   S	print special registers\n\
   t	print backtrace\n\
@@ -175,6 +171,35 @@
 				     "r" (loops) : "ctr");
 }
 
+/* Print an address in numeric and symbolic form (if possible) */
+static void xmon_print_symbol(unsigned long address, const char *mid,
+			      const char *after)
+{
+	char *modname;
+	const char *name = NULL;
+	unsigned long offset, size;
+	static char tmpstr[128];
+
+	printf("%.8lx", address);
+	if (setjmp(bus_error_jmp) == 0) {
+		debugger_fault_handler = handle_fault;
+		sync();
+		name = kallsyms_lookup(address, &size, &offset, &modname,
+				       tmpstr);
+		sync();
+		/* wait a little while to see if we get a machine check */
+		__delay(200);
+	}
+	debugger_fault_handler = NULL;
+
+	if (name) {
+		printf("%s%s+%#lx/%#lx", mid, name, offset, size);
+		if (modname)
+			printf(" [%s]", modname);
+	}
+	printf("%s", after);
+}
+
 static void get_tb(unsigned *p)
 {
 	unsigned hi, lo, hiagain;
@@ -454,7 +479,7 @@
 			dump();
 			break;
 		case 'l':
-			sysmap_lookup();
+			symbol_lookup();
 			break;
 		case 'r':
 			if (excp != NULL)
@@ -466,9 +491,6 @@
 			else
 				excprint(excp);
 			break;
-		case 'M':
-			print_sysmap();
-			break;
 		case 'S':
 			super_regs();
 			break;
@@ -825,20 +847,19 @@
 	for (; sp != 0; sp = stack[0]) {
 		if (mread(sp, stack, sizeof(stack)) != sizeof(stack))
 			break;
-		pretty_print_addr(stack[1]);
-		printf(" ");
+		printf("[%.8lx] ", stack);
+		xmon_print_symbol(stack[1], " ", "\n");
 		if (stack[1] == (unsigned) &ret_from_except
 		    || stack[1] == (unsigned) &ret_from_except_full
 		    || stack[1] == (unsigned) &ret_from_syscall) {
 			if (mread(sp+16, &regs, sizeof(regs)) != sizeof(regs))
 				break;
-			printf("\nexception:%x [%x] %x ", regs.trap, sp+16,
+			printf("exception:%x [%x] %x\n", regs.trap, sp+16,
 			       regs.nip);
 			sp = regs.gpr[1];
 			if (mread(sp, stack, sizeof(stack)) != sizeof(stack))
 				break;
 		}
-		printf("\n");
 	}
 }
 
@@ -859,11 +880,10 @@
 #ifdef CONFIG_SMP
 	printf("cpu %d: ", smp_processor_id());
 #endif /* CONFIG_SMP */
-	printf("vector: %x at pc = ", fp->trap);
-	pretty_print_addr(fp->nip);
-	printf(", lr = ");
-	pretty_print_addr(fp->link);
-	printf("\nmsr = %x, sp = %x [%x]\n", fp->msr, fp->gpr[1], fp);
+	printf("vector: %x at pc=", fp->trap);
+	xmon_print_symbol(fp->nip, ": ", ", lr=");
+	xmon_print_symbol(fp->link, ": ", "\n");
+	printf("msr = %x, sp = %x [%x]\n", fp->msr, fp->gpr[1], fp);
 	trap = TRAP(fp);
 	if (trap == 0x300 || trap == 0x600)
 		printf("dar = %x, dsisr = %x\n", fp->dar, fp->dsisr);
@@ -951,24 +971,6 @@
 extern char dec_exc;
 
 void
-print_sysmap(void)
-{
-	extern char *sysmap;
-	if ( sysmap ) {
-		printf("System.map: \n");
-		if( setjmp(bus_error_jmp) == 0 ) {
-			debugger_fault_handler = handle_fault;
-			sync();
-			xmon_puts(sysmap);
-			sync();
-		}
-		debugger_fault_handler = NULL;
-	}
-	else
-		printf("No System.map\n");
-}
-
-void
 super_regs(void)
 {
 	int i, cmd;
@@ -1738,7 +1740,7 @@
 		printf("invalid register name '%%%s'\n", regname);
 		return 0;
 	} else if (c == '$') {
-		static char symname[64];
+		static char symname[128];
 		int i;
 		for (i=0; i<63; i++) {
 			c = inchar();
@@ -1749,7 +1751,14 @@
 			symname[i] = c;
 		}
 		symname[i++] = 0;
-		*vp = xmon_symbol_to_addr(symname);
+		*vp = 0;
+		if (setjmp(bus_error_jmp) == 0) {
+			debugger_fault_handler = handle_fault;
+			sync();
+			*vp = kallsyms_lookup_name(symname);
+			sync();
+		}
+		debugger_fault_handler = NULL;
 		if (!(*vp)) {
 			printf("unknown symbol\n");
 			return 0;
@@ -1840,169 +1849,34 @@
 	lineptr = str;
 }
 
-void
-sysmap_lookup(void)
+static void
+symbol_lookup(void)
 {
 	int type = inchar();
 	unsigned addr;
-	static char tmp[64];
-	char* cur;
+	static char tmp[128];
 
-	extern char *sysmap;
-	extern unsigned long sysmap_size;
-	if ( !sysmap || !sysmap_size )
-		return;
-
-	switch(type) {
-		case 'a':
-			if (scanhex(&addr)) {
-				pretty_print_addr(addr);
-				printf("\n");
-			}
-			termch = 0;
-			break;
-		case 's':
-			getstring(tmp, 64);
-			if( setjmp(bus_error_jmp) == 0 ) {
-				debugger_fault_handler = handle_fault;
-				sync();
-				cur = sysmap;
-				do {
-					cur = strstr(cur, tmp);
-					if (cur) {
-						static char res[64];
-						char *p, *d;
-						p = cur;
-						while(p > sysmap && *p != 10)
-							p--;
-						if (*p == 10) p++;
-						d = res;
-						while(*p && p < (sysmap + sysmap_size) && *p != 10)
-							*(d++) = *(p++);
-						*(d++) = 0;
-						printf("%s\n", res);
-						cur++;
-					}
-				} while (cur);
-				sync();
-			}
-			debugger_fault_handler = NULL;
-			termch = 0;
-			break;
-	}
-}
-
-static int
-pretty_print_addr(unsigned long addr)
-{
-	char *sym;
-	unsigned long saddr;
-	
-	printf("%08x", addr);
-	sym = xmon_find_symbol(addr, &saddr);
-	if (sym)
-		printf(" (%s+0x%x)", sym, addr-saddr);
-	return (sym != 0);
-}
-
-char*
-xmon_find_symbol(unsigned long addr, unsigned long* saddr)
-{
-	static char rbuffer[64];
-	char *p, *ep, *limit;
-	unsigned long prev, next;
-	char* psym;
-
-	extern char *sysmap;
-	extern unsigned long sysmap_size;
-	if ( !sysmap || !sysmap_size )
-		return NULL;
-	
-	prev = 0;
-	psym = NULL;
-	p = sysmap;
-	limit = p + sysmap_size;
-	if( setjmp(bus_error_jmp) == 0 ) {
-		debugger_fault_handler = handle_fault;
-		sync();
-		do {
-			next = simple_strtoul(p, &p, 16);
-			if (next > addr && prev <= addr) {
-				if (!psym)
-					goto bail;
-				ep = rbuffer;
-				p = psym;
-				while(*p && p < limit && *p == 32)
-					p++;
-				while(*p && p < limit && *p != 10 && (ep - rbuffer) < 63)
-					*(ep++) = *(p++);
-				*(ep++) = 0;
-				if (saddr)
-					*saddr = prev;
-				debugger_fault_handler = NULL;
-				return rbuffer;
-			}
-			prev = next;
-			psym = p;
-			while(*p && p < limit && *p != 10)
-				p++;
-			if (*p) p++;
-		} while(*p && p < limit && next);
-bail:
-		sync();
-	}
-	debugger_fault_handler = NULL;
-	return NULL;
-}
-
-unsigned long
-xmon_symbol_to_addr(char* symbol)
-{
-	char *p, *cur;
-	char *match = NULL;
-	int goodness = 0;
-	int result = 0;
-	
-	extern char *sysmap;
-	extern unsigned long sysmap_size;
-	if ( !sysmap || !sysmap_size )
-		return 0;
-
-	if( setjmp(bus_error_jmp) == 0 ) {
-		debugger_fault_handler = handle_fault;
-		sync();
-		cur = sysmap;
-		while(cur) {
-			cur = strstr(cur, symbol);
-			if (cur) {
-				int gd = 1;
-
-				/* best match if equal, better match if
-				 * begins with
-				 */
-				if (cur == sysmap || *(cur-1) == ' ') {
-					gd++;
-					if (cur[strlen(symbol)] == 10)
-						gd++;
-				}
-				if (gd > goodness) {
-					match = cur;
-					goodness = gd;
-					if (gd == 3)
-						break;
-				}
-				cur++;
-			}
-		}	
-		if (goodness) {
-			p = match;
-			while(p > sysmap && *p != 10)
-				p--;
-			if (*p == 10) p++;
-			result = simple_strtoul(p, &p, 16);
+	switch (type) {
+	case 'a':
+		if (scanhex(&addr))
+			xmon_print_symbol(addr, ": ", "\n");
+		termch = 0;
+		break;
+	case 's':
+		getstring(tmp, 64);
+		if (setjmp(bus_error_jmp) == 0) {
+			debugger_fault_handler = handle_fault;
+			sync();
+			addr = kallsyms_lookup_name(tmp);
+			if (addr)
+				printf("%s: %lx\n", tmp, addr);
+			else
+				printf("Symbol '%s' not found.\n", tmp);
+			sync();
 		}
-		sync();
+		debugger_fault_handler = NULL;
+		termch = 0;
+		break;
 	}
-	debugger_fault_handler = NULL;
-	return result;
-}		
+}
+
diff --git a/arch/ppc64/Kconfig b/arch/ppc64/Kconfig
index 5cb3438..0f1fa28 100644
--- a/arch/ppc64/Kconfig
+++ b/arch/ppc64/Kconfig
@@ -323,7 +323,7 @@
 	bool
 
 config PCI
-	bool
+	bool "support for PCI devices" if (EMBEDDED && PPC_ISERIES)
 	default y
 	help
 	  Find out whether your system includes a PCI bus. PCI is the name of
diff --git a/arch/ppc64/Makefile b/arch/ppc64/Makefile
index 691f300..33c752c 100644
--- a/arch/ppc64/Makefile
+++ b/arch/ppc64/Makefile
@@ -35,9 +35,9 @@
 CROSS32LD	:= $(LD) -m elf32ppc
 CROSS32OBJCOPY	:= $(OBJCOPY)
 endif
-AS              := $(AS) -a64
-LD              := $(LD) -m elf64ppc
-CC		:= $(CC) -m64
+override AS	+= -a64
+override LD	+= -m elf64ppc
+override CC	+= -m64
 endif
 
 export CROSS32CC CROSS32AS CROSS32LD CROSS32OBJCOPY
diff --git a/arch/ppc64/kernel/HvLpEvent.c b/arch/ppc64/kernel/HvLpEvent.c
index f8f1963..90032b1 100644
--- a/arch/ppc64/kernel/HvLpEvent.c
+++ b/arch/ppc64/kernel/HvLpEvent.c
@@ -12,7 +12,7 @@
 #include <asm/system.h>
 #include <asm/iSeries/HvLpEvent.h>
 #include <asm/iSeries/HvCallEvent.h>
-#include <asm/iSeries/LparData.h>
+#include <asm/iSeries/ItLpNaca.h>
 
 /* Array of LpEvent handler functions */
 LpEventHandler lpEventHandler[HvLpEvent_Type_NumTypes];
diff --git a/arch/ppc64/kernel/ItLpQueue.c b/arch/ppc64/kernel/ItLpQueue.c
index c923a81..cdea00d 100644
--- a/arch/ppc64/kernel/ItLpQueue.c
+++ b/arch/ppc64/kernel/ItLpQueue.c
@@ -16,7 +16,6 @@
 #include <asm/iSeries/ItLpQueue.h>
 #include <asm/iSeries/HvLpEvent.h>
 #include <asm/iSeries/HvCallEvent.h>
-#include <asm/iSeries/LparData.h>
 
 static __inline__ int set_inUse( struct ItLpQueue * lpQueue )
 {
diff --git a/arch/ppc64/kernel/Makefile b/arch/ppc64/kernel/Makefile
index 96d90b0..b5e167c 100644
--- a/arch/ppc64/kernel/Makefile
+++ b/arch/ppc64/kernel/Makefile
@@ -16,14 +16,13 @@
 
 obj-$(CONFIG_PPC_OF) +=	of_device.o
 
-pci-obj-$(CONFIG_PPC_ISERIES)	+= iSeries_pci.o iSeries_pci_reset.o
+pci-obj-$(CONFIG_PPC_ISERIES)	+= iSeries_pci.o iSeries_irq.o \
+				iSeries_VpdInfo.o
 pci-obj-$(CONFIG_PPC_MULTIPLATFORM)	+= pci_dn.o pci_direct_iommu.o
 
 obj-$(CONFIG_PCI)	+= pci.o pci_iommu.o iomap.o $(pci-obj-y)
 
-obj-$(CONFIG_PPC_ISERIES) += iSeries_irq.o \
-			     iSeries_VpdInfo.o XmPciLpEvent.o \
-			     HvCall.o HvLpConfig.o LparData.o \
+obj-$(CONFIG_PPC_ISERIES) += HvCall.o HvLpConfig.o LparData.o \
 			     iSeries_setup.o ItLpQueue.o hvCall.o \
 			     mf.o HvLpEvent.o iSeries_proc.o iSeries_htab.o \
 			     iSeries_iommu.o
diff --git a/arch/ppc64/kernel/XmPciLpEvent.c b/arch/ppc64/kernel/XmPciLpEvent.c
deleted file mode 100644
index 809c9bc..0000000
--- a/arch/ppc64/kernel/XmPciLpEvent.c
+++ /dev/null
@@ -1,190 +0,0 @@
-/*
- * File XmPciLpEvent.h created by Wayne Holm on Mon Jan 15 2001.
- *
- * This module handles PCI interrupt events sent by the iSeries Hypervisor.
-*/
-
-#include <linux/config.h>
-#include <linux/pci.h>
-#include <linux/init.h>
-#include <linux/threads.h>
-#include <linux/smp.h>
-#include <linux/param.h>
-#include <linux/string.h>
-#include <linux/bootmem.h>
-#include <linux/ide.h>
-
-#include <asm/iSeries/HvTypes.h>
-#include <asm/iSeries/HvLpEvent.h>
-#include <asm/iSeries/HvCallPci.h>
-#include <asm/iSeries/XmPciLpEvent.h>
-#include <asm/ppcdebug.h>
-
-static long Pci_Interrupt_Count;
-static long Pci_Event_Count;
-
-enum XmPciLpEvent_Subtype {
-	XmPciLpEvent_BusCreated	   = 0,		// PHB has been created
-	XmPciLpEvent_BusError	   = 1,		// PHB has failed
-	XmPciLpEvent_BusFailed	   = 2,		// Msg to Secondary, Primary failed bus
-	XmPciLpEvent_NodeFailed	   = 4,		// Multi-adapter bridge has failed
-	XmPciLpEvent_NodeRecovered = 5,		// Multi-adapter bridge has recovered
-	XmPciLpEvent_BusRecovered  = 12,	// PHB has been recovered
-	XmPciLpEvent_UnQuiesceBus  = 18,	// Secondary bus unqiescing
-	XmPciLpEvent_BridgeError   = 21,	// Bridge Error
-	XmPciLpEvent_SlotInterrupt = 22		// Slot interrupt
-};
-
-struct XmPciLpEvent_BusInterrupt {
-	HvBusNumber	busNumber;
-	HvSubBusNumber	subBusNumber;
-};
-
-struct XmPciLpEvent_NodeInterrupt {
-	HvBusNumber	busNumber;
-	HvSubBusNumber	subBusNumber;
-	HvAgentId	deviceId;
-};
-
-struct XmPciLpEvent {
-	struct HvLpEvent hvLpEvent;
-
-	union {
-		u64 alignData;			// Align on an 8-byte boundary
-
-		struct {
-			u32		fisr;
-			HvBusNumber	busNumber;
-			HvSubBusNumber	subBusNumber;
-			HvAgentId	deviceId;
-		} slotInterrupt;
-
-		struct XmPciLpEvent_BusInterrupt busFailed;
-		struct XmPciLpEvent_BusInterrupt busRecovered;
-		struct XmPciLpEvent_BusInterrupt busCreated;
-
-		struct XmPciLpEvent_NodeInterrupt nodeFailed;
-		struct XmPciLpEvent_NodeInterrupt nodeRecovered;
-
-	} eventData;
-
-};
-
-static void intReceived(struct XmPciLpEvent *eventParm,
-		struct pt_regs *regsParm);
-
-static void XmPciLpEvent_handler(struct HvLpEvent *eventParm,
-		struct pt_regs *regsParm)
-{
-#ifdef CONFIG_PCI
-#if 0
-	PPCDBG(PPCDBG_BUSWALK, "XmPciLpEvent_handler, type 0x%x\n",
-			eventParm->xType);
-#endif
-	++Pci_Event_Count;
-
-	if (eventParm && (eventParm->xType == HvLpEvent_Type_PciIo)) {
-		switch (eventParm->xFlags.xFunction) {
-		case HvLpEvent_Function_Int:
-			intReceived((struct XmPciLpEvent *)eventParm, regsParm);
-			break;
-		case HvLpEvent_Function_Ack:
-			printk(KERN_ERR
-				"XmPciLpEvent.c: unexpected ack received\n");
-			break;
-		default:
-			printk(KERN_ERR
-				"XmPciLpEvent.c: unexpected event function %d\n",
-				(int)eventParm->xFlags.xFunction);
-			break;
-		}
-	} else if (eventParm)
-		printk(KERN_ERR
-			"XmPciLpEvent.c: Unrecognized PCI event type 0x%x\n",
-			(int)eventParm->xType);
-	else
-		printk(KERN_ERR "XmPciLpEvent.c: NULL event received\n");
-#endif
-}
-
-static void intReceived(struct XmPciLpEvent *eventParm,
-		struct pt_regs *regsParm)
-{
-	int irq;
-
-	++Pci_Interrupt_Count;
-#if 0
-	PPCDBG(PPCDBG_BUSWALK, "PCI: XmPciLpEvent.c: intReceived\n");
-#endif
-
-	switch (eventParm->hvLpEvent.xSubtype) {
-	case XmPciLpEvent_SlotInterrupt:
-		irq = eventParm->hvLpEvent.xCorrelationToken;
-		/* Dispatch the interrupt handlers for this irq */
-		ppc_irq_dispatch_handler(regsParm, irq);
-		HvCallPci_eoi(eventParm->eventData.slotInterrupt.busNumber,
-			eventParm->eventData.slotInterrupt.subBusNumber,
-			eventParm->eventData.slotInterrupt.deviceId);
-		break;
-		/* Ignore error recovery events for now */
-	case XmPciLpEvent_BusCreated:
-		printk(KERN_INFO "XmPciLpEvent.c: system bus %d created\n",
-			eventParm->eventData.busCreated.busNumber);
-		break;
-	case XmPciLpEvent_BusError:
-	case XmPciLpEvent_BusFailed:
-		printk(KERN_INFO "XmPciLpEvent.c: system bus %d failed\n",
-			eventParm->eventData.busFailed.busNumber);
-		break;
-	case XmPciLpEvent_BusRecovered:
-	case XmPciLpEvent_UnQuiesceBus:
-		printk(KERN_INFO "XmPciLpEvent.c: system bus %d recovered\n",
-			eventParm->eventData.busRecovered.busNumber);
-		break;
-	case XmPciLpEvent_NodeFailed:
-	case XmPciLpEvent_BridgeError:
-		printk(KERN_INFO
-			"XmPciLpEvent.c: multi-adapter bridge %d/%d/%d failed\n",
-			eventParm->eventData.nodeFailed.busNumber,
-			eventParm->eventData.nodeFailed.subBusNumber,
-			eventParm->eventData.nodeFailed.deviceId);
-		break;
-	case XmPciLpEvent_NodeRecovered:
-		printk(KERN_INFO
-			"XmPciLpEvent.c: multi-adapter bridge %d/%d/%d recovered\n",
-			eventParm->eventData.nodeRecovered.busNumber,
-			eventParm->eventData.nodeRecovered.subBusNumber,
-			eventParm->eventData.nodeRecovered.deviceId);
-		break;
-	default:
-		printk(KERN_ERR
-			"XmPciLpEvent.c: unrecognized event subtype 0x%x\n",
-			eventParm->hvLpEvent.xSubtype);
-		break;
-	}
-}
-
-
-/* This should be called sometime prior to buswalk (init_IRQ would be good) */
-int XmPciLpEvent_init()
-{
-	int xRc;
-
-	PPCDBG(PPCDBG_BUSWALK,
-			"XmPciLpEvent_init, Register Event type 0x%04X\n",
-			HvLpEvent_Type_PciIo);
-
-	xRc = HvLpEvent_registerHandler(HvLpEvent_Type_PciIo,
-			&XmPciLpEvent_handler);
-	if (xRc == 0) {
-		xRc = HvLpEvent_openPath(HvLpEvent_Type_PciIo, 0);
-		if (xRc != 0)
-			printk(KERN_ERR
-				"XmPciLpEvent.c: open event path failed with rc 0x%x\n",
-				xRc);
-	} else
-		printk(KERN_ERR
-			"XmPciLpEvent.c: register handler failed with rc 0x%x\n",
-			xRc);
-	return xRc;
-}
diff --git a/arch/ppc64/kernel/asm-offsets.c b/arch/ppc64/kernel/asm-offsets.c
index 0094ac7..abb9e5b 100644
--- a/arch/ppc64/kernel/asm-offsets.c
+++ b/arch/ppc64/kernel/asm-offsets.c
@@ -31,7 +31,6 @@
 
 #include <asm/paca.h>
 #include <asm/lppaca.h>
-#include <asm/iSeries/ItLpQueue.h>
 #include <asm/iSeries/HvLpEvent.h>
 #include <asm/rtas.h>
 #include <asm/cputable.h>
diff --git a/arch/ppc64/kernel/dma.c b/arch/ppc64/kernel/dma.c
index ce714c9..4da8e31 100644
--- a/arch/ppc64/kernel/dma.c
+++ b/arch/ppc64/kernel/dma.c
@@ -15,8 +15,10 @@
 
 static struct dma_mapping_ops *get_dma_ops(struct device *dev)
 {
+#ifdef CONFIG_PCI
 	if (dev->bus == &pci_bus_type)
 		return &pci_dma_ops;
+#endif
 #ifdef CONFIG_IBMVIO
 	if (dev->bus == &vio_bus_type)
 		return &vio_dma_ops;
@@ -37,8 +39,10 @@
 
 int dma_set_mask(struct device *dev, u64 dma_mask)
 {
+#ifdef CONFIG_PCI
 	if (dev->bus == &pci_bus_type)
 		return pci_set_dma_mask(to_pci_dev(dev), dma_mask);
+#endif
 #ifdef CONFIG_IBMVIO
 	if (dev->bus == &vio_bus_type)
 		return -EIO;
diff --git a/arch/ppc64/kernel/eeh.c b/arch/ppc64/kernel/eeh.c
index d63d41f..af5272f 100644
--- a/arch/ppc64/kernel/eeh.c
+++ b/arch/ppc64/kernel/eeh.c
@@ -505,7 +505,7 @@
 	pte_t *ptep;
 	unsigned long pa;
 
-	ptep = find_linux_pte(ioremap_mm.pgd, token);
+	ptep = find_linux_pte(init_mm.pgd, token);
 	if (!ptep)
 		return token;
 	pa = pte_pfn(*ptep) << PAGE_SHIFT;
diff --git a/arch/ppc64/kernel/head.S b/arch/ppc64/kernel/head.S
index 346dbf6..02c8f4e 100644
--- a/arch/ppc64/kernel/head.S
+++ b/arch/ppc64/kernel/head.S
@@ -2121,10 +2121,6 @@
 swapper_pg_dir:
 	.space	4096
 
-	.globl	ioremap_dir
-ioremap_dir:
-	.space	4096
-
 #ifdef CONFIG_SMP
 /* 1 page segment table per cpu (max 48, cpu0 allocated at STAB0_PHYS_ADDR) */
 	.globl	stab_array
diff --git a/arch/ppc64/kernel/iSeries_VpdInfo.c b/arch/ppc64/kernel/iSeries_VpdInfo.c
index a6f0ff2..d11c732 100644
--- a/arch/ppc64/kernel/iSeries_VpdInfo.c
+++ b/arch/ppc64/kernel/iSeries_VpdInfo.c
@@ -1,31 +1,31 @@
-/************************************************************************/
-/* File iSeries_vpdInfo.c created by Allan Trautman on Fri Feb  2 2001. */
-/************************************************************************/
-/* This code gets the card location of the hardware                     */
-/* Copyright (C) 20yy  <Allan H Trautman> <IBM Corp>                    */
-/*                                                                      */
-/* This program is free software; you can redistribute it and/or modify */
-/* it under the terms of the GNU General Public License as published by */
-/* the Free Software Foundation; either version 2 of the License, or    */
-/* (at your option) any later version.                                  */
-/*                                                                      */
-/* This program is distributed in the hope that it will be useful,      */ 
-/* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
-/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
-/* GNU General Public License for more details.                         */
-/*                                                                      */
-/* You should have received a copy of the GNU General Public License    */ 
-/* along with this program; if not, write to the:                       */
-/* Free Software Foundation, Inc.,                                      */ 
-/* 59 Temple Place, Suite 330,                                          */ 
-/* Boston, MA  02111-1307  USA                                          */
-/************************************************************************/
-/* Change Activity:                                                     */
-/*   Created, Feb 2, 2001                                               */
-/*   Ported to ppc64, August 20, 2001                                   */
-/* End Change Activity                                                  */
-/************************************************************************/
-#include <linux/config.h>
+/*
+ * File iSeries_vpdInfo.c created by Allan Trautman on Fri Feb  2 2001.
+ *
+ * This code gets the card location of the hardware
+ * Copyright (C) 2001  <Allan H Trautman> <IBM Corp>
+ * Copyright (C) 2005  Stephen Rothwel, IBM Corp
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the:
+ * Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330,
+ * Boston, MA  02111-1307  USA
+ *
+ * Change Activity:
+ *   Created, Feb 2, 2001
+ *   Ported to ppc64, August 20, 2001
+ * End Change Activity
+ */
 #include <linux/init.h>
 #include <linux/module.h>
 #include <linux/pci.h>
@@ -34,30 +34,25 @@
 
 #include <asm/iSeries/HvCallPci.h>
 #include <asm/iSeries/HvTypes.h>
-#include <asm/iSeries/mf.h>
-#include <asm/iSeries/LparData.h>
 #include <asm/iSeries/iSeries_pci.h>
-#include "pci.h"
 
 /*
  * Size of Bus VPD data
  */
 #define BUS_VPDSIZE      1024
+
 /*
  * Bus Vpd Tags
  */
-#define  VpdEndOfDataTag   0x78
 #define  VpdEndOfAreaTag   0x79
 #define  VpdIdStringTag    0x82
 #define  VpdVendorAreaTag  0x84
+
 /*
  * Mfg Area Tags
  */
-#define  VpdFruFlag       0x4647     // "FG"
 #define  VpdFruFrameId    0x4649     // "FI"
 #define  VpdSlotMapFormat 0x4D46     // "MF"
-#define  VpdAsmPartNumber 0x504E     // "PN"
-#define  VpdFruSerial     0x534E     // "SN"
 #define  VpdSlotMap       0x534D     // "SM"
 
 /*
@@ -79,74 +74,33 @@
 	char CardLocation[3];
 	char Parms[8];
 	char Reserved[2];
-}; 
+};
 typedef struct SlotMapStruct SlotMap;
 #define SLOT_ENTRY_SIZE   16
 
 /*
- * Formats the device information.
- * - Pass in pci_dev* pointer to the device.
- * - Pass in buffer to place the data.  Danger here is the buffer must
- *   be as big as the client says it is.   Should be at least 128 bytes.
- * Return will the length of the string data put in the buffer.
- * Format:
- * PCI: Bus  0, Device 26, Vendor 0x12AE  Frame  1, Card  C10  Ethernet
- * controller
- */
-int iSeries_Device_Information(struct pci_dev *PciDev, char *buffer,
-		int BufferSize)
-{
-	struct iSeries_Device_Node *DevNode =
-		(struct iSeries_Device_Node *)PciDev->sysdata;
-	int len;
-
-	if (DevNode == NULL)
-		return sprintf(buffer,
-				"PCI: iSeries_Device_Information DevNode is NULL");
-
-	if (BufferSize < 128)
-		return 0;
-
-	len = sprintf(buffer, "PCI: Bus%3d, Device%3d, Vendor %04X ",
-			ISERIES_BUS(DevNode), PCI_SLOT(PciDev->devfn),
-			PciDev->vendor);
-	len += sprintf(buffer + len, "Frame%3d, Card %4s  ",
-			DevNode->FrameId, DevNode->CardLocation);
-#ifdef CONFIG_PCI
-	if (pci_class_name(PciDev->class >> 8) == 0)
-		len += sprintf(buffer + len, "0x%04X  ",
-				(int)(PciDev->class >> 8));
-	else
-		len += sprintf(buffer + len, "%s",
-				pci_class_name(PciDev->class >> 8));
-#endif
-	return len;
-}
-
-/*
  * Parse the Slot Area
  */
-void iSeries_Parse_SlotArea(SlotMap *MapPtr, int MapLen,
-		struct iSeries_Device_Node *DevNode)
+static void __init iSeries_Parse_SlotArea(SlotMap *MapPtr, int MapLen,
+		HvAgentId agent, u8 *PhbId, char card[4])
 {
 	int SlotMapLen = MapLen;
 	SlotMap *SlotMapPtr = MapPtr;
 
 	/*
-	 * Parse Slot label until we find the one requrested
+	 * Parse Slot label until we find the one requested
 	 */
 	while (SlotMapLen > 0) {
-		if (SlotMapPtr->AgentId == DevNode->AgentId ) {
+		if (SlotMapPtr->AgentId == agent) {
 			/*
 			 * If Phb wasn't found, grab the entry first one found.
 			 */
-			if (DevNode->PhbId == 0xff)
-				DevNode->PhbId = SlotMapPtr->PhbId; 
+			if (*PhbId == 0xff)
+				*PhbId = SlotMapPtr->PhbId;
 			/* Found it, extract the data. */
-			if (SlotMapPtr->PhbId == DevNode->PhbId ) {
-	        		memcpy(&DevNode->CardLocation,
-						&SlotMapPtr->CardLocation, 3);
-				DevNode->CardLocation[3]  = 0;
+			if (SlotMapPtr->PhbId == *PhbId) {
+				memcpy(card, &SlotMapPtr->CardLocation, 3);
+				card[3]  = 0;
 				break;
 			}
 		}
@@ -159,8 +113,9 @@
 /*
  * Parse the Mfg Area
  */
-static void iSeries_Parse_MfgArea(u8 *AreaData, int AreaLen,
-		struct iSeries_Device_Node *DevNode)
+static void __init iSeries_Parse_MfgArea(u8 *AreaData, int AreaLen,
+		HvAgentId agent, u8 *PhbId,
+		u8 *frame, char card[4])
 {
 	MfgArea *MfgAreaPtr = (MfgArea *)AreaData;
 	int MfgAreaLen = AreaLen;
@@ -171,7 +126,7 @@
 		int MfgTagLen = MfgAreaPtr->TagLength;
 		/* Frame ID         (FI 4649020310 ) */
 		if (MfgAreaPtr->Tag == VpdFruFrameId)		/* FI  */
-			DevNode->FrameId = MfgAreaPtr->AreaData1;
+			*frame = MfgAreaPtr->AreaData1;
 		/* Slot Map Format  (MF 4D46020004 ) */
 		else if (MfgAreaPtr->Tag == VpdSlotMapFormat)	/* MF  */
 			SlotMapFmt = (MfgAreaPtr->AreaData1 * 256)
@@ -183,10 +138,11 @@
 			if (SlotMapFmt == 0x1004)
 				SlotMapPtr = (SlotMap *)((char *)MfgAreaPtr
 						+ MFG_ENTRY_SIZE + 1);
- 	    		else
+			else
 				SlotMapPtr = (SlotMap *)((char *)MfgAreaPtr
 						+ MFG_ENTRY_SIZE);
-	    		iSeries_Parse_SlotArea(SlotMapPtr, MfgTagLen, DevNode);
+			iSeries_Parse_SlotArea(SlotMapPtr, MfgTagLen,
+					agent, PhbId, card);
 		}
 		/*
 		 * Point to the next Mfg Area
@@ -194,19 +150,19 @@
 		 */
 		MfgAreaPtr = (MfgArea *)((char *)MfgAreaPtr + MfgTagLen
 				+ MFG_ENTRY_SIZE);
-		MfgAreaLen -= (MfgTagLen + MFG_ENTRY_SIZE); 
-	}	
+		MfgAreaLen -= (MfgTagLen + MFG_ENTRY_SIZE);
+	}
 }
 
 /*
  * Look for "BUS".. Data is not Null terminated.
  * PHBID of 0xFF indicates PHB was not found in VPD Data.
  */
-static int iSeries_Parse_PhbId(u8 *AreaPtr, int AreaLength)
+static int __init iSeries_Parse_PhbId(u8 *AreaPtr, int AreaLength)
 {
 	u8 *PhbPtr = AreaPtr;
 	int DataLen = AreaLength;
-	char PhbId = 0xFF;                   
+	char PhbId = 0xFF;
 
 	while (DataLen > 0) {
 		if ((*PhbPtr == 'B') && (*(PhbPtr + 1) == 'U')
@@ -216,7 +172,7 @@
 				++PhbPtr;
 			PhbId = (*PhbPtr & 0x0F);
 			break;
-        	}
+		}
 		++PhbPtr;
 		--DataLen;
 	}
@@ -226,52 +182,90 @@
 /*
  * Parse out the VPD Areas
  */
-static void iSeries_Parse_Vpd(u8 *VpdData, int VpdDataLen,
-		struct iSeries_Device_Node *DevNode)
+static void __init iSeries_Parse_Vpd(u8 *VpdData, int VpdDataLen,
+		HvAgentId agent, u8 *frame, char card[4])
 {
 	u8 *TagPtr = VpdData;
 	int DataLen = VpdDataLen - 3;
+	u8 PhbId;
 
 	while ((*TagPtr != VpdEndOfAreaTag) && (DataLen > 0)) {
-		int AreaLen = *(TagPtr + 1) + (*(TagPtr + 2) * 256);	
+		int AreaLen = *(TagPtr + 1) + (*(TagPtr + 2) * 256);
 		u8 *AreaData  = TagPtr + 3;
 
 		if (*TagPtr == VpdIdStringTag)
-			DevNode->PhbId = iSeries_Parse_PhbId(AreaData, AreaLen);
+			PhbId = iSeries_Parse_PhbId(AreaData, AreaLen);
 		else if (*TagPtr == VpdVendorAreaTag)
-	    		iSeries_Parse_MfgArea(AreaData, AreaLen, DevNode);
+			iSeries_Parse_MfgArea(AreaData, AreaLen,
+					agent, &PhbId, frame, card);
 		/* Point to next Area. */
 		TagPtr  = AreaData + AreaLen;
 		DataLen -= AreaLen;
 	}
-}    
+}
 
-void iSeries_Get_Location_Code(struct iSeries_Device_Node *DevNode)
+static void __init iSeries_Get_Location_Code(u16 bus, HvAgentId agent,
+		u8 *frame, char card[4])
 {
 	int BusVpdLen = 0;
-	u8 *BusVpdPtr = (u8 *)kmalloc(BUS_VPDSIZE, GFP_KERNEL);
+	u8 *BusVpdPtr = kmalloc(BUS_VPDSIZE, GFP_KERNEL);
 
 	if (BusVpdPtr == NULL) {
 		printk("PCI: Bus VPD Buffer allocation failure.\n");
 		return;
 	}
-	BusVpdLen = HvCallPci_getBusVpd(ISERIES_BUS(DevNode),
-					ISERIES_HV_ADDR(BusVpdPtr),
+	BusVpdLen = HvCallPci_getBusVpd(bus, ISERIES_HV_ADDR(BusVpdPtr),
 					BUS_VPDSIZE);
 	if (BusVpdLen == 0) {
-		kfree(BusVpdPtr);
 		printk("PCI: Bus VPD Buffer zero length.\n");
-		return;
+		goto out_free;
 	}
 	/* printk("PCI: BusVpdPtr: %p, %d\n",BusVpdPtr, BusVpdLen); */
 	/* Make sure this is what I think it is */
 	if (*BusVpdPtr != VpdIdStringTag) {	/* 0x82 */
 		printk("PCI: Bus VPD Buffer missing starting tag.\n");
-		kfree(BusVpdPtr);
+		goto out_free;
+	}
+	iSeries_Parse_Vpd(BusVpdPtr, BusVpdLen, agent, frame, card);
+out_free:
+	kfree(BusVpdPtr);
+}
+
+/*
+ * Prints the device information.
+ * - Pass in pci_dev* pointer to the device.
+ * - Pass in the device count
+ *
+ * Format:
+ * PCI: Bus  0, Device 26, Vendor 0x12AE  Frame  1, Card  C10  Ethernet
+ * controller
+ */
+void __init iSeries_Device_Information(struct pci_dev *PciDev, int count)
+{
+	struct iSeries_Device_Node *DevNode = PciDev->sysdata;
+	u16 bus;
+	u8 frame;
+	char card[4];
+	HvSubBusNumber subbus;
+	HvAgentId agent;
+
+	if (DevNode == NULL) {
+		printk("%d. PCI: iSeries_Device_Information DevNode is NULL\n",
+				count);
 		return;
 	}
-	iSeries_Parse_Vpd(BusVpdPtr,BusVpdLen, DevNode);
-	sprintf(DevNode->Location, "Frame%3d, Card %-4s", DevNode->FrameId,
-			DevNode->CardLocation);
-	kfree(BusVpdPtr);
+
+	bus = ISERIES_BUS(DevNode);
+	subbus = ISERIES_SUBBUS(DevNode);
+	agent = ISERIES_PCI_AGENTID(ISERIES_GET_DEVICE_FROM_SUBBUS(subbus),
+			ISERIES_GET_FUNCTION_FROM_SUBBUS(subbus));
+	iSeries_Get_Location_Code(bus, agent, &frame, card);
+
+	printk("%d. PCI: Bus%3d, Device%3d, Vendor %04X Frame%3d, Card %4s  ",
+			count, bus, PCI_SLOT(PciDev->devfn), PciDev->vendor,
+			frame, card);
+	if (pci_class_name(PciDev->class >> 8) == 0)
+		printk("0x%04X\n", (int)(PciDev->class >> 8));
+	else
+		printk("%s\n", pci_class_name(PciDev->class >> 8));
 }
diff --git a/arch/ppc64/kernel/iSeries_iommu.c b/arch/ppc64/kernel/iSeries_iommu.c
index 4e1a47c..f8ff1bb 100644
--- a/arch/ppc64/kernel/iSeries_iommu.c
+++ b/arch/ppc64/kernel/iSeries_iommu.c
@@ -83,7 +83,7 @@
 	}
 }
 
-
+#ifdef CONFIG_PCI
 /*
  * This function compares the known tables to find an iommu_table
  * that has already been built for hardware TCEs.
@@ -159,6 +159,7 @@
 	else
 		kfree(tbl);
 }
+#endif
 
 static void iommu_dev_setup_iSeries(struct pci_dev *dev) { }
 static void iommu_bus_setup_iSeries(struct pci_bus *bus) { }
diff --git a/arch/ppc64/kernel/iSeries_irq.c b/arch/ppc64/kernel/iSeries_irq.c
index f831d25..77376c1 100644
--- a/arch/ppc64/kernel/iSeries_irq.c
+++ b/arch/ppc64/kernel/iSeries_irq.c
@@ -1,27 +1,29 @@
-/************************************************************************/
-/* This module supports the iSeries PCI bus interrupt handling          */
-/* Copyright (C) 20yy  <Robert L Holtorf> <IBM Corp>                    */
-/*                                                                      */
-/* This program is free software; you can redistribute it and/or modify */
-/* it under the terms of the GNU General Public License as published by */
-/* the Free Software Foundation; either version 2 of the License, or    */
-/* (at your option) any later version.                                  */
-/*                                                                      */
-/* This program is distributed in the hope that it will be useful,      */ 
-/* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
-/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
-/* GNU General Public License for more details.                         */
-/*                                                                      */
-/* You should have received a copy of the GNU General Public License    */ 
-/* along with this program; if not, write to the:                       */
-/* Free Software Foundation, Inc.,                                      */ 
-/* 59 Temple Place, Suite 330,                                          */ 
-/* Boston, MA  02111-1307  USA                                          */
-/************************************************************************/
-/* Change Activity:                                                     */
-/*   Created, December 13, 2000 by Wayne Holm                           */ 
-/* End Change Activity                                                  */
-/************************************************************************/
+/*
+ * This module supports the iSeries PCI bus interrupt handling
+ * Copyright (C) 20yy  <Robert L Holtorf> <IBM Corp>
+ * Copyright (C) 2004-2005 IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the:
+ * Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330,
+ * Boston, MA  02111-1307  USA
+ *
+ * Change Activity:
+ *   Created, December 13, 2000 by Wayne Holm
+ * End Change Activity
+ */
+#include <linux/config.h>
 #include <linux/pci.h>
 #include <linux/init.h>
 #include <linux/threads.h>
@@ -30,30 +32,15 @@
 #include <linux/string.h>
 #include <linux/bootmem.h>
 #include <linux/ide.h>
-
 #include <linux/irq.h>
 #include <linux/spinlock.h>
-#include <asm/ppcdebug.h>
 
+#include <asm/ppcdebug.h>
+#include <asm/iSeries/HvTypes.h>
+#include <asm/iSeries/HvLpEvent.h>
 #include <asm/iSeries/HvCallPci.h>
 #include <asm/iSeries/HvCallXm.h>
 #include <asm/iSeries/iSeries_irq.h>
-#include <asm/iSeries/XmPciLpEvent.h>
-
-static unsigned int iSeries_startup_IRQ(unsigned int irq);
-static void iSeries_shutdown_IRQ(unsigned int irq);
-static void iSeries_enable_IRQ(unsigned int irq);
-static void iSeries_disable_IRQ(unsigned int irq);
-static void iSeries_end_IRQ(unsigned int irq);
-
-static hw_irq_controller iSeries_IRQ_handler = {
-	.typename = "iSeries irq controller",
-	.startup = iSeries_startup_IRQ,
-	.shutdown = iSeries_shutdown_IRQ,
-	.enable = iSeries_enable_IRQ,
-	.disable = iSeries_disable_IRQ,
-	.end = iSeries_end_IRQ
-};
 
 /* This maps virtual irq numbers to real irqs */
 unsigned int virt_irq_to_real_map[NR_IRQS];
@@ -62,37 +49,187 @@
 /* Note: the pcnet32 driver assumes irq numbers < 2 aren't valid. :( */
 static int next_virtual_irq = 2;
 
-/* This is called by init_IRQ.  set in ppc_md.init_IRQ by iSeries_setup.c */
-void __init iSeries_init_IRQ(void)
+static long Pci_Interrupt_Count;
+static long Pci_Event_Count;
+
+enum XmPciLpEvent_Subtype {
+	XmPciLpEvent_BusCreated		= 0,	// PHB has been created
+	XmPciLpEvent_BusError		= 1,	// PHB has failed
+	XmPciLpEvent_BusFailed		= 2,	// Msg to Secondary, Primary failed bus
+	XmPciLpEvent_NodeFailed		= 4,	// Multi-adapter bridge has failed
+	XmPciLpEvent_NodeRecovered	= 5,	// Multi-adapter bridge has recovered
+	XmPciLpEvent_BusRecovered	= 12,	// PHB has been recovered
+	XmPciLpEvent_UnQuiesceBus	= 18,	// Secondary bus unqiescing
+	XmPciLpEvent_BridgeError	= 21,	// Bridge Error
+	XmPciLpEvent_SlotInterrupt	= 22	// Slot interrupt
+};
+
+struct XmPciLpEvent_BusInterrupt {
+	HvBusNumber	busNumber;
+	HvSubBusNumber	subBusNumber;
+};
+
+struct XmPciLpEvent_NodeInterrupt {
+	HvBusNumber	busNumber;
+	HvSubBusNumber	subBusNumber;
+	HvAgentId	deviceId;
+};
+
+struct XmPciLpEvent {
+	struct HvLpEvent hvLpEvent;
+
+	union {
+		u64 alignData;			// Align on an 8-byte boundary
+
+		struct {
+			u32		fisr;
+			HvBusNumber	busNumber;
+			HvSubBusNumber	subBusNumber;
+			HvAgentId	deviceId;
+		} slotInterrupt;
+
+		struct XmPciLpEvent_BusInterrupt busFailed;
+		struct XmPciLpEvent_BusInterrupt busRecovered;
+		struct XmPciLpEvent_BusInterrupt busCreated;
+
+		struct XmPciLpEvent_NodeInterrupt nodeFailed;
+		struct XmPciLpEvent_NodeInterrupt nodeRecovered;
+
+	} eventData;
+
+};
+
+static void intReceived(struct XmPciLpEvent *eventParm,
+		struct pt_regs *regsParm)
 {
-	/* Register PCI event handler and open an event path */
-	XmPciLpEvent_init();
+	int irq;
+
+	++Pci_Interrupt_Count;
+
+	switch (eventParm->hvLpEvent.xSubtype) {
+	case XmPciLpEvent_SlotInterrupt:
+		irq = eventParm->hvLpEvent.xCorrelationToken;
+		/* Dispatch the interrupt handlers for this irq */
+		ppc_irq_dispatch_handler(regsParm, irq);
+		HvCallPci_eoi(eventParm->eventData.slotInterrupt.busNumber,
+			eventParm->eventData.slotInterrupt.subBusNumber,
+			eventParm->eventData.slotInterrupt.deviceId);
+		break;
+		/* Ignore error recovery events for now */
+	case XmPciLpEvent_BusCreated:
+		printk(KERN_INFO "intReceived: system bus %d created\n",
+			eventParm->eventData.busCreated.busNumber);
+		break;
+	case XmPciLpEvent_BusError:
+	case XmPciLpEvent_BusFailed:
+		printk(KERN_INFO "intReceived: system bus %d failed\n",
+			eventParm->eventData.busFailed.busNumber);
+		break;
+	case XmPciLpEvent_BusRecovered:
+	case XmPciLpEvent_UnQuiesceBus:
+		printk(KERN_INFO "intReceived: system bus %d recovered\n",
+			eventParm->eventData.busRecovered.busNumber);
+		break;
+	case XmPciLpEvent_NodeFailed:
+	case XmPciLpEvent_BridgeError:
+		printk(KERN_INFO
+			"intReceived: multi-adapter bridge %d/%d/%d failed\n",
+			eventParm->eventData.nodeFailed.busNumber,
+			eventParm->eventData.nodeFailed.subBusNumber,
+			eventParm->eventData.nodeFailed.deviceId);
+		break;
+	case XmPciLpEvent_NodeRecovered:
+		printk(KERN_INFO
+			"intReceived: multi-adapter bridge %d/%d/%d recovered\n",
+			eventParm->eventData.nodeRecovered.busNumber,
+			eventParm->eventData.nodeRecovered.subBusNumber,
+			eventParm->eventData.nodeRecovered.deviceId);
+		break;
+	default:
+		printk(KERN_ERR
+			"intReceived: unrecognized event subtype 0x%x\n",
+			eventParm->hvLpEvent.xSubtype);
+		break;
+	}
+}
+
+static void XmPciLpEvent_handler(struct HvLpEvent *eventParm,
+		struct pt_regs *regsParm)
+{
+#ifdef CONFIG_PCI
+	++Pci_Event_Count;
+
+	if (eventParm && (eventParm->xType == HvLpEvent_Type_PciIo)) {
+		switch (eventParm->xFlags.xFunction) {
+		case HvLpEvent_Function_Int:
+			intReceived((struct XmPciLpEvent *)eventParm, regsParm);
+			break;
+		case HvLpEvent_Function_Ack:
+			printk(KERN_ERR
+				"XmPciLpEvent_handler: unexpected ack received\n");
+			break;
+		default:
+			printk(KERN_ERR
+				"XmPciLpEvent_handler: unexpected event function %d\n",
+				(int)eventParm->xFlags.xFunction);
+			break;
+		}
+	} else if (eventParm)
+		printk(KERN_ERR
+			"XmPciLpEvent_handler: Unrecognized PCI event type 0x%x\n",
+			(int)eventParm->xType);
+	else
+		printk(KERN_ERR "XmPciLpEvent_handler: NULL event received\n");
+#endif
 }
 
 /*
- * This is called out of iSeries_scan_slot to allocate an IRQ for an EADS slot
- * It calculates the irq value for the slot.
- * Note that subBusNumber is always 0 (at the moment at least).
+ * This is called by init_IRQ.  set in ppc_md.init_IRQ by iSeries_setup.c
+ * It must be called before the bus walk.
  */
-int __init iSeries_allocate_IRQ(HvBusNumber busNumber,
-		HvSubBusNumber subBusNumber, HvAgentId deviceId)
+void __init iSeries_init_IRQ(void)
 {
-	unsigned int realirq, virtirq;
-	u8 idsel = (deviceId >> 4);
-	u8 function = deviceId & 7;
+	/* Register PCI event handler and open an event path */
+	int xRc;
 
-	virtirq = next_virtual_irq++;
-	realirq = ((busNumber - 1) << 6) + ((idsel - 1) << 3) + function;
-	virt_irq_to_real_map[virtirq] = realirq;
-
-	irq_desc[virtirq].handler = &iSeries_IRQ_handler;
-	return virtirq;
+	xRc = HvLpEvent_registerHandler(HvLpEvent_Type_PciIo,
+			&XmPciLpEvent_handler);
+	if (xRc == 0) {
+		xRc = HvLpEvent_openPath(HvLpEvent_Type_PciIo, 0);
+		if (xRc != 0)
+			printk(KERN_ERR "iSeries_init_IRQ: open event path "
+					"failed with rc 0x%x\n", xRc);
+	} else
+		printk(KERN_ERR "iSeries_init_IRQ: register handler "
+				"failed with rc 0x%x\n", xRc);
 }
 
 #define REAL_IRQ_TO_BUS(irq)	((((irq) >> 6) & 0xff) + 1)
 #define REAL_IRQ_TO_IDSEL(irq)	((((irq) >> 3) & 7) + 1)
 #define REAL_IRQ_TO_FUNC(irq)	((irq) & 7)
 
+/*
+ * This will be called by device drivers (via enable_IRQ)
+ * to enable INTA in the bridge interrupt status register.
+ */
+static void iSeries_enable_IRQ(unsigned int irq)
+{
+	u32 bus, deviceId, function, mask;
+	const u32 subBus = 0;
+	unsigned int rirq = virt_irq_to_real_map[irq];
+
+	/* The IRQ has already been locked by the caller */
+	bus = REAL_IRQ_TO_BUS(rirq);
+	function = REAL_IRQ_TO_FUNC(rirq);
+	deviceId = (REAL_IRQ_TO_IDSEL(rirq) << 4) + function;
+
+	/* Unmask secondary INTA */
+	mask = 0x80000000;
+	HvCallPci_unmaskInterrupts(bus, subBus, deviceId, mask);
+	PPCDBG(PPCDBG_BUSWALK, "iSeries_enable_IRQ 0x%02X.%02X.%02X 0x%04X\n",
+			bus, subBus, deviceId, irq);
+}
+
 /* This is called by iSeries_activate_IRQs */
 static unsigned int iSeries_startup_IRQ(unsigned int irq)
 {
@@ -131,7 +268,7 @@
 			desc->handler->startup(irq);
 			spin_unlock_irqrestore(&desc->lock, flags);
 		}
-    	}
+	}
 }
 
 /*  this is not called anywhere currently */
@@ -173,29 +310,7 @@
 	mask = 0x80000000;
 	HvCallPci_maskInterrupts(bus, subBus, deviceId, mask);
 	PPCDBG(PPCDBG_BUSWALK, "iSeries_disable_IRQ 0x%02X.%02X.%02X 0x%04X\n",
-	       bus, subBus, deviceId, irq);
-}
-
-/*
- * This will be called by device drivers (via enable_IRQ)
- * to enable INTA in the bridge interrupt status register.
- */
-static void iSeries_enable_IRQ(unsigned int irq)
-{
-	u32 bus, deviceId, function, mask;
-	const u32 subBus = 0;
-	unsigned int rirq = virt_irq_to_real_map[irq];
-
-	/* The IRQ has already been locked by the caller */
-	bus = REAL_IRQ_TO_BUS(rirq);
-	function = REAL_IRQ_TO_FUNC(rirq);
-	deviceId = (REAL_IRQ_TO_IDSEL(rirq) << 4) + function;
-
-	/* Unmask secondary INTA */
-	mask = 0x80000000;
-	HvCallPci_unmaskInterrupts(bus, subBus, deviceId, mask);
-	PPCDBG(PPCDBG_BUSWALK, "iSeries_enable_IRQ 0x%02X.%02X.%02X 0x%04X\n",
-	       bus, subBus, deviceId, irq);
+			bus, subBus, deviceId, irq);
 }
 
 /*
@@ -207,3 +322,32 @@
 static void iSeries_end_IRQ(unsigned int irq)
 {
 }
+
+static hw_irq_controller iSeries_IRQ_handler = {
+	.typename = "iSeries irq controller",
+	.startup = iSeries_startup_IRQ,
+	.shutdown = iSeries_shutdown_IRQ,
+	.enable = iSeries_enable_IRQ,
+	.disable = iSeries_disable_IRQ,
+	.end = iSeries_end_IRQ
+};
+
+/*
+ * This is called out of iSeries_scan_slot to allocate an IRQ for an EADS slot
+ * It calculates the irq value for the slot.
+ * Note that subBusNumber is always 0 (at the moment at least).
+ */
+int __init iSeries_allocate_IRQ(HvBusNumber busNumber,
+		HvSubBusNumber subBusNumber, HvAgentId deviceId)
+{
+	unsigned int realirq, virtirq;
+	u8 idsel = (deviceId >> 4);
+	u8 function = deviceId & 7;
+
+	virtirq = next_virtual_irq++;
+	realirq = ((busNumber - 1) << 6) + ((idsel - 1) << 3) + function;
+	virt_irq_to_real_map[virtirq] = realirq;
+
+	irq_desc[virtirq].handler = &iSeries_IRQ_handler;
+	return virtirq;
+}
diff --git a/arch/ppc64/kernel/iSeries_pci.c b/arch/ppc64/kernel/iSeries_pci.c
index bd4c255..356e4fd 100644
--- a/arch/ppc64/kernel/iSeries_pci.c
+++ b/arch/ppc64/kernel/iSeries_pci.c
@@ -38,9 +38,7 @@
 #include <asm/iommu.h>
 
 #include <asm/iSeries/HvCallPci.h>
-#include <asm/iSeries/HvCallSm.h>
 #include <asm/iSeries/HvCallXm.h>
-#include <asm/iSeries/LparData.h>
 #include <asm/iSeries/iSeries_irq.h>
 #include <asm/iSeries/iSeries_pci.h>
 #include <asm/iSeries/mf.h>
@@ -225,10 +223,7 @@
 	node->DsaAddr.Dsa.busNumber = Bus;
 	node->DsaAddr.Dsa.subBusNumber = SubBus;
 	node->DsaAddr.Dsa.deviceId = 0x10;
-	node->AgentId = AgentId;
 	node->DevFn = PCI_DEVFN(ISERIES_ENCODE_DEVICE(AgentId), Function);
-	node->IoRetry = 0;
-	iSeries_Get_Location_Code(node);
 	return node;
 }
 
@@ -302,7 +297,6 @@
 {
 	struct pci_dev *pdev = NULL;
 	struct iSeries_Device_Node *node;
-	char Buffer[256];
     	int DeviceCount = 0;
 
 	PPCDBG(PPCDBG_BUSWALK, "iSeries_pcibios_fixup Entry.\n"); 
@@ -324,9 +318,7 @@
 					"pdev 0x%p <==> DevNode 0x%p\n",
 					pdev, node);
 			allocate_device_bars(pdev);
-			iSeries_Device_Information(pdev, Buffer,
-					sizeof(Buffer));
-			printk("%d. %s\n", DeviceCount, Buffer);
+			iSeries_Device_Information(pdev, DeviceCount);
 			iommu_devnode_init_iSeries(node);
 		} else
 			printk("PCI: Device Tree not found for 0x%016lX\n",
@@ -499,7 +491,6 @@
 
 			++DeviceCount;
 			node = build_device_node(Bus, SubBus, EADsIdSel, Function);
-			node->Vendor = VendorId;
 			node->Irq = Irq;
 			node->LogicalSlot = BridgeInfo->logicalSlotNumber;
 
@@ -661,38 +652,34 @@
  * Check Return Code
  * -> On Failure, print and log information.
  *    Increment Retry Count, if exceeds max, panic partition.
- * -> If in retry, print and log success 
  *
  * PCI: Device 23.90 ReadL I/O Error( 0): 0x1234
  * PCI: Device 23.90 ReadL Retry( 1)
  * PCI: Device 23.90 ReadL Retry Successful(1)
  */
 static int CheckReturnCode(char *TextHdr, struct iSeries_Device_Node *DevNode,
-		u64 ret)
+		int *retry, u64 ret)
 {
 	if (ret != 0)  {
 		++Pci_Error_Count;
-		++DevNode->IoRetry;
+		(*retry)++;
 		printk("PCI: %s: Device 0x%04X:%02X  I/O Error(%2d): 0x%04X\n",
 				TextHdr, DevNode->DsaAddr.Dsa.busNumber, DevNode->DevFn,
-				DevNode->IoRetry, (int)ret);
+				*retry, (int)ret);
 		/*
 		 * Bump the retry and check for retry count exceeded.
 		 * If, Exceeded, panic the system.
 		 */
-		if ((DevNode->IoRetry > Pci_Retry_Max) &&
+		if (((*retry) > Pci_Retry_Max) &&
 				(Pci_Error_Flag > 0)) {
 			mf_display_src(0xB6000103);
-			panic_timeout = 0; 
+			panic_timeout = 0;
 			panic("PCI: Hardware I/O Error, SRC B6000103, "
 					"Automatic Reboot Disabled.\n");
 		}
 		return -1;	/* Retry Try */
 	}
-	/* If retry was in progress, log success and rest retry count */
-	if (DevNode->IoRetry > 0)
-		DevNode->IoRetry = 0;
-	return 0; 
+	return 0;
 }
 
 /*
@@ -738,6 +725,7 @@
 {
 	u64 BarOffset;
 	u64 dsa;
+	int retry = 0;
 	struct HvCallPci_LoadReturn ret;
 	struct iSeries_Device_Node *DevNode =
 		xlate_iomm_address(IoAddress, &dsa, &BarOffset);
@@ -757,7 +745,7 @@
 	do {
 		++Pci_Io_Read_Count;
 		HvCall3Ret16(HvCallPciBarLoad8, &ret, dsa, BarOffset, 0);
-	} while (CheckReturnCode("RDB", DevNode, ret.rc) != 0);
+	} while (CheckReturnCode("RDB", DevNode, &retry, ret.rc) != 0);
 
 	return (u8)ret.value;
 }
@@ -767,6 +755,7 @@
 {
 	u64 BarOffset;
 	u64 dsa;
+	int retry = 0;
 	struct HvCallPci_LoadReturn ret;
 	struct iSeries_Device_Node *DevNode =
 		xlate_iomm_address(IoAddress, &dsa, &BarOffset);
@@ -787,7 +776,7 @@
 		++Pci_Io_Read_Count;
 		HvCall3Ret16(HvCallPciBarLoad16, &ret, dsa,
 				BarOffset, 0);
-	} while (CheckReturnCode("RDW", DevNode, ret.rc) != 0);
+	} while (CheckReturnCode("RDW", DevNode, &retry, ret.rc) != 0);
 
 	return swab16((u16)ret.value);
 }
@@ -797,6 +786,7 @@
 {
 	u64 BarOffset;
 	u64 dsa;
+	int retry = 0;
 	struct HvCallPci_LoadReturn ret;
 	struct iSeries_Device_Node *DevNode =
 		xlate_iomm_address(IoAddress, &dsa, &BarOffset);
@@ -817,7 +807,7 @@
 		++Pci_Io_Read_Count;
 		HvCall3Ret16(HvCallPciBarLoad32, &ret, dsa,
 				BarOffset, 0);
-	} while (CheckReturnCode("RDL", DevNode, ret.rc) != 0);
+	} while (CheckReturnCode("RDL", DevNode, &retry, ret.rc) != 0);
 
 	return swab32((u32)ret.value);
 }
@@ -834,6 +824,7 @@
 {
 	u64 BarOffset;
 	u64 dsa;
+	int retry = 0;
 	u64 rc;
 	struct iSeries_Device_Node *DevNode =
 		xlate_iomm_address(IoAddress, &dsa, &BarOffset);
@@ -853,7 +844,7 @@
 	do {
 		++Pci_Io_Write_Count;
 		rc = HvCall4(HvCallPciBarStore8, dsa, BarOffset, data, 0);
-	} while (CheckReturnCode("WWB", DevNode, rc) != 0);
+	} while (CheckReturnCode("WWB", DevNode, &retry, rc) != 0);
 }
 EXPORT_SYMBOL(iSeries_Write_Byte);
 
@@ -861,6 +852,7 @@
 {
 	u64 BarOffset;
 	u64 dsa;
+	int retry = 0;
 	u64 rc;
 	struct iSeries_Device_Node *DevNode =
 		xlate_iomm_address(IoAddress, &dsa, &BarOffset);
@@ -880,7 +872,7 @@
 	do {
 		++Pci_Io_Write_Count;
 		rc = HvCall4(HvCallPciBarStore16, dsa, BarOffset, swab16(data), 0);
-	} while (CheckReturnCode("WWW", DevNode, rc) != 0);
+	} while (CheckReturnCode("WWW", DevNode, &retry, rc) != 0);
 }
 EXPORT_SYMBOL(iSeries_Write_Word);
 
@@ -888,6 +880,7 @@
 {
 	u64 BarOffset;
 	u64 dsa;
+	int retry = 0;
 	u64 rc;
 	struct iSeries_Device_Node *DevNode =
 		xlate_iomm_address(IoAddress, &dsa, &BarOffset);
@@ -907,6 +900,6 @@
 	do {
 		++Pci_Io_Write_Count;
 		rc = HvCall4(HvCallPciBarStore32, dsa, BarOffset, swab32(data), 0);
-	} while (CheckReturnCode("WWL", DevNode, rc) != 0);
+	} while (CheckReturnCode("WWL", DevNode, &retry, rc) != 0);
 }
 EXPORT_SYMBOL(iSeries_Write_Long);
diff --git a/arch/ppc64/kernel/iSeries_pci_reset.c b/arch/ppc64/kernel/iSeries_pci_reset.c
deleted file mode 100644
index 0f785e4..0000000
--- a/arch/ppc64/kernel/iSeries_pci_reset.c
+++ /dev/null
@@ -1,104 +0,0 @@
-#define PCIFR(...)
-/************************************************************************/
-/* File iSeries_pci_reset.c created by Allan Trautman on Mar 21 2001.   */
-/************************************************************************/
-/* This code supports the pci interface on the IBM iSeries systems.     */
-/* Copyright (C) 20yy  <Allan H Trautman> <IBM Corp>                    */
-/*                                                                      */
-/* This program is free software; you can redistribute it and/or modify */
-/* it under the terms of the GNU General Public License as published by */
-/* the Free Software Foundation; either version 2 of the License, or    */
-/* (at your option) any later version.                                  */
-/*                                                                      */
-/* This program is distributed in the hope that it will be useful,      */ 
-/* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
-/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
-/* GNU General Public License for more details.                         */
-/*                                                                      */
-/* You should have received a copy of the GNU General Public License    */ 
-/* along with this program; if not, write to the:                       */
-/* Free Software Foundation, Inc.,                                      */ 
-/* 59 Temple Place, Suite 330,                                          */ 
-/* Boston, MA  02111-1307  USA                                          */
-/************************************************************************/
-/* Change Activity:                                                     */
-/*   Created, March 20, 2001                                            */
-/*   April 30, 2001, Added return codes on functions.                   */
-/*   September 10, 2001, Ported to ppc64.                               */
-/* End Change Activity                                                  */
-/************************************************************************/
-#include <linux/kernel.h>
-#include <linux/init.h>
-#include <linux/module.h>
-#include <linux/pci.h>
-#include <linux/irq.h>
-#include <linux/delay.h>
-
-#include <asm/io.h>
-#include <asm/iSeries/HvCallPci.h>
-#include <asm/iSeries/HvTypes.h>
-#include <asm/iSeries/mf.h>
-#include <asm/pci.h>
-
-#include <asm/iSeries/iSeries_pci.h>
-#include "pci.h"
-
-/*
- * Interface to toggle the reset line
- * Time is in .1 seconds, need for seconds.
- */
-int iSeries_Device_ToggleReset(struct pci_dev *PciDev, int AssertTime,
-		int DelayTime)
-{
-	unsigned int AssertDelay, WaitDelay;
-	struct iSeries_Device_Node *DeviceNode =
-		(struct iSeries_Device_Node *)PciDev->sysdata;
-
- 	if (DeviceNode == NULL) { 
-		printk("PCI: Pci Reset Failed, Device Node not found for pci_dev %p\n",
-				PciDev);
-		return -1;
-	}
-	/*
-	 * Set defaults, Assert is .5 second, Wait is 3 seconds.
-	 */
-	if (AssertTime == 0)
-		AssertDelay = 500;
-	else
-		AssertDelay = AssertTime * 100;
-
-	if (DelayTime == 0)
-		WaitDelay = 3000;
-	else
-		WaitDelay = DelayTime * 100;
-
-	/*
-	 * Assert reset
-	 */
-	DeviceNode->ReturnCode = HvCallPci_setSlotReset(ISERIES_BUS(DeviceNode),
-			0x00, DeviceNode->AgentId, 1);
-	if (DeviceNode->ReturnCode == 0) {
-		msleep(AssertDelay);			/* Sleep for the time */
-		DeviceNode->ReturnCode =
-			HvCallPci_setSlotReset(ISERIES_BUS(DeviceNode),
-					0x00, DeviceNode->AgentId, 0);
-
-		/*
-   		 * Wait for device to reset
-		 */
-		msleep(WaitDelay);
-	}
-	if (DeviceNode->ReturnCode == 0)
-		PCIFR("Slot 0x%04X.%02 Reset\n", ISERIES_BUS(DeviceNode),
-				DeviceNode->AgentId);
-	else {
-		printk("PCI: Slot 0x%04X.%02X Reset Failed, RCode: %04X\n",
-				ISERIES_BUS(DeviceNode), DeviceNode->AgentId,
-				DeviceNode->ReturnCode);
-		PCIFR("Slot 0x%04X.%02X Reset Failed, RCode: %04X\n",
-				ISERIES_BUS(DeviceNode), DeviceNode->AgentId,
-				DeviceNode->ReturnCode);
-	}
-	return DeviceNode->ReturnCode;
-}
-EXPORT_SYMBOL(iSeries_Device_ToggleReset);
diff --git a/arch/ppc64/kernel/iSeries_proc.c b/arch/ppc64/kernel/iSeries_proc.c
index 0cc58dd..356bd99 100644
--- a/arch/ppc64/kernel/iSeries_proc.c
+++ b/arch/ppc64/kernel/iSeries_proc.c
@@ -28,8 +28,7 @@
 #include <asm/iSeries/ItLpQueue.h>
 #include <asm/iSeries/HvCallXm.h>
 #include <asm/iSeries/IoHriMainStore.h>
-#include <asm/iSeries/LparData.h>
-#include <asm/iSeries/iSeries_proc.h>
+#include <asm/iSeries/IoHriProcessorVpd.h>
 
 static int __init iseries_proc_create(void)
 {
diff --git a/arch/ppc64/kernel/iSeries_setup.c b/arch/ppc64/kernel/iSeries_setup.c
index 6d06eb5..b319624 100644
--- a/arch/ppc64/kernel/iSeries_setup.c
+++ b/arch/ppc64/kernel/iSeries_setup.c
@@ -47,7 +47,7 @@
 #include <asm/paca.h>
 #include <asm/cache.h>
 #include <asm/sections.h>
-#include <asm/iSeries/LparData.h>
+#include <asm/abs_addr.h>
 #include <asm/iSeries/HvCallHpt.h>
 #include <asm/iSeries/HvLpConfig.h>
 #include <asm/iSeries/HvCallEvent.h>
@@ -55,10 +55,12 @@
 #include <asm/iSeries/HvCallXm.h>
 #include <asm/iSeries/ItLpQueue.h>
 #include <asm/iSeries/IoHriMainStore.h>
-#include <asm/iSeries/iSeries_proc.h>
 #include <asm/iSeries/mf.h>
 #include <asm/iSeries/HvLpEvent.h>
 #include <asm/iSeries/iSeries_irq.h>
+#include <asm/iSeries/IoHriProcessorVpd.h>
+#include <asm/iSeries/ItVpdAreas.h>
+#include <asm/iSeries/LparMap.h>
 
 extern void hvlog(char *fmt, ...);
 
@@ -74,7 +76,11 @@
 static void build_iSeries_Memory_Map(void);
 static void setup_iSeries_cache_sizes(void);
 static void iSeries_bolt_kernel(unsigned long saddr, unsigned long eaddr);
+#ifdef CONFIG_PCI
 extern void iSeries_pci_final_fixup(void);
+#else
+static void iSeries_pci_final_fixup(void) { }
+#endif
 
 /* Global Variables */
 static unsigned long procFreqHz;
@@ -874,6 +880,10 @@
 }
 __setup("spread_lpevents=", set_spread_lpevents);
 
+#ifndef CONFIG_PCI
+void __init iSeries_init_IRQ(void) { }
+#endif
+
 void __init iSeries_early_setup(void)
 {
 	iSeries_fixup_klimit();
diff --git a/arch/ppc64/kernel/iSeries_smp.c b/arch/ppc64/kernel/iSeries_smp.c
index ba1f084..f74386e 100644
--- a/arch/ppc64/kernel/iSeries_smp.c
+++ b/arch/ppc64/kernel/iSeries_smp.c
@@ -38,9 +38,7 @@
 #include <asm/io.h>
 #include <asm/smp.h>
 #include <asm/paca.h>
-#include <asm/iSeries/LparData.h>
 #include <asm/iSeries/HvCall.h>
-#include <asm/iSeries/HvCallCfg.h>
 #include <asm/time.h>
 #include <asm/ppcdebug.h>
 #include <asm/machdep.h>
diff --git a/arch/ppc64/kernel/idle.c b/arch/ppc64/kernel/idle.c
index f24ce2b..bdf13b4 100644
--- a/arch/ppc64/kernel/idle.c
+++ b/arch/ppc64/kernel/idle.c
@@ -42,6 +42,11 @@
 static unsigned long maxYieldTime = 0;
 static unsigned long minYieldTime = 0xffffffffffffffffUL;
 
+static inline void process_iSeries_events(void)
+{
+	asm volatile ("li 0,0x5555; sc" : : : "r0", "r3");
+}
+
 static void yield_shared_processor(void)
 {
 	unsigned long tb;
@@ -292,7 +297,7 @@
 		if (need_resched())
 			schedule();
 
-		if (cpu_is_offline(_smp_processor_id()) &&
+		if (cpu_is_offline(raw_smp_processor_id()) &&
 		    system_state == SYSTEM_RUNNING)
 			cpu_die();
 	}
diff --git a/arch/ppc64/kernel/irq.c b/arch/ppc64/kernel/irq.c
index 4fd7f20..d860467 100644
--- a/arch/ppc64/kernel/irq.c
+++ b/arch/ppc64/kernel/irq.c
@@ -52,7 +52,7 @@
 #include <asm/cache.h>
 #include <asm/prom.h>
 #include <asm/ptrace.h>
-#include <asm/iSeries/LparData.h>
+#include <asm/iSeries/ItLpQueue.h>
 #include <asm/machdep.h>
 #include <asm/paca.h>
 
diff --git a/arch/ppc64/kernel/lparcfg.c b/arch/ppc64/kernel/lparcfg.c
index a8fd32d..387923f 100644
--- a/arch/ppc64/kernel/lparcfg.c
+++ b/arch/ppc64/kernel/lparcfg.c
@@ -28,12 +28,12 @@
 #include <asm/uaccess.h>
 #include <asm/iSeries/HvLpConfig.h>
 #include <asm/lppaca.h>
-#include <asm/iSeries/LparData.h>
 #include <asm/hvcall.h>
 #include <asm/cputable.h>
 #include <asm/rtas.h>
 #include <asm/system.h>
 #include <asm/time.h>
+#include <asm/iSeries/ItExtVpdPanel.h>
 
 #define MODULE_VERS "1.6"
 #define MODULE_NAME "lparcfg"
diff --git a/arch/ppc64/kernel/mf.c b/arch/ppc64/kernel/mf.c
index 5aca7e8..d98bebf 100644
--- a/arch/ppc64/kernel/mf.c
+++ b/arch/ppc64/kernel/mf.c
@@ -40,7 +40,6 @@
 #include <asm/iSeries/vio.h>
 #include <asm/iSeries/mf.h>
 #include <asm/iSeries/HvLpConfig.h>
-#include <asm/iSeries/ItSpCommArea.h>
 #include <asm/iSeries/ItLpQueue.h>
 
 /*
diff --git a/arch/ppc64/kernel/process.c b/arch/ppc64/kernel/process.c
index cdfecbe..aba8955 100644
--- a/arch/ppc64/kernel/process.c
+++ b/arch/ppc64/kernel/process.c
@@ -58,14 +58,6 @@
 struct task_struct *last_task_used_altivec = NULL;
 #endif
 
-struct mm_struct ioremap_mm = {
-	.pgd		= ioremap_dir,
-	.mm_users	= ATOMIC_INIT(2),
-	.mm_count	= ATOMIC_INIT(1),
-	.cpu_vm_mask	= CPU_MASK_ALL,
-	.page_table_lock = SPIN_LOCK_UNLOCKED,
-};
-
 /*
  * Make sure the floating-point register state in the
  * the thread_struct is up to date for task tsk.
diff --git a/arch/ppc64/kernel/prom.c b/arch/ppc64/kernel/prom.c
index eb6538b..47727a6 100644
--- a/arch/ppc64/kernel/prom.c
+++ b/arch/ppc64/kernel/prom.c
@@ -884,6 +884,7 @@
 {
 	char *type = get_flat_dt_prop(node, "device_type", NULL);
 	u32 *prop;
+	unsigned long size;
 
 	/* We are scanning "cpu" nodes only */
 	if (type == NULL || strcmp(type, "cpu") != 0)
@@ -929,6 +930,17 @@
 		cur_cpu_spec->cpu_user_features |= PPC_FEATURE_HAS_ALTIVEC;
 	}
 
+	/*
+	 * Check for an SMT capable CPU and set the CPU feature. We do
+	 * this by looking at the size of the ibm,ppc-interrupt-server#s
+	 * property
+	 */
+	prop = (u32 *)get_flat_dt_prop(node, "ibm,ppc-interrupt-server#s",
+				       &size);
+	cur_cpu_spec->cpu_features &= ~CPU_FTR_SMT;
+	if (prop && ((size / sizeof(u32)) > 1))
+		cur_cpu_spec->cpu_features |= CPU_FTR_SMT;
+
 	return 0;
 }
 
diff --git a/arch/ppc64/kernel/ras.c b/arch/ppc64/kernel/ras.c
index 1c4c796..3c00f7b 100644
--- a/arch/ppc64/kernel/ras.c
+++ b/arch/ppc64/kernel/ras.c
@@ -47,7 +47,6 @@
 #include <asm/cache.h>
 #include <asm/prom.h>
 #include <asm/ptrace.h>
-#include <asm/iSeries/LparData.h>
 #include <asm/machdep.h>
 #include <asm/rtas.h>
 #include <asm/ppcdebug.h>
diff --git a/arch/ppc64/kernel/rtc.c b/arch/ppc64/kernel/rtc.c
index 6798905..de02aed 100644
--- a/arch/ppc64/kernel/rtc.c
+++ b/arch/ppc64/kernel/rtc.c
@@ -42,10 +42,8 @@
 #include <asm/time.h>
 #include <asm/rtas.h>
 
-#include <asm/iSeries/LparData.h>
 #include <asm/iSeries/mf.h>
 #include <asm/machdep.h>
-#include <asm/iSeries/ItSpCommArea.h>
 
 extern int piranha_simulator;
 
diff --git a/arch/ppc64/kernel/setup.c b/arch/ppc64/kernel/setup.c
index dce198d..8e439a8 100644
--- a/arch/ppc64/kernel/setup.c
+++ b/arch/ppc64/kernel/setup.c
@@ -41,7 +41,6 @@
 #include <asm/smp.h>
 #include <asm/elf.h>
 #include <asm/machdep.h>
-#include <asm/iSeries/LparData.h>
 #include <asm/paca.h>
 #include <asm/ppcdebug.h>
 #include <asm/time.h>
@@ -57,6 +56,8 @@
 #include <asm/cache.h>
 #include <asm/page.h>
 #include <asm/mmu.h>
+#include <asm/lmb.h>
+#include <asm/iSeries/ItLpNaca.h>
 
 #ifdef DEBUG
 #define DBG(fmt...) udbg_printf(fmt)
diff --git a/arch/ppc64/kernel/sys_ppc32.c b/arch/ppc64/kernel/sys_ppc32.c
index 9c8e317..118436e 100644
--- a/arch/ppc64/kernel/sys_ppc32.c
+++ b/arch/ppc64/kernel/sys_ppc32.c
@@ -741,6 +741,7 @@
 
 asmlinkage int sys32_pciconfig_iobase(u32 which, u32 in_bus, u32 in_devfn)
 {
+#ifdef CONFIG_PCI
 	struct pci_controller* hose;
 	struct list_head *ln;
 	struct pci_bus *bus = NULL;
@@ -786,7 +787,7 @@
 	case IOBASE_ISA_MEM:
 		return -EINVAL;
 	}
-
+#endif	/* CONFIG_PCI */
 	return -EOPNOTSUPP;
 }
 
diff --git a/arch/ppc64/kernel/vio.c b/arch/ppc64/kernel/vio.c
index 79f2dc7..0c0ba71 100644
--- a/arch/ppc64/kernel/vio.c
+++ b/arch/ppc64/kernel/vio.c
@@ -41,20 +41,25 @@
 static struct iommu_table *vio_build_iommu_table(struct vio_dev *);
 static int vio_num_address_cells;
 #endif
-static struct vio_dev *vio_bus_device; /* fake "parent" device */
+#ifdef CONFIG_PPC_ISERIES
+static struct iommu_table veth_iommu_table;
+static struct iommu_table vio_iommu_table;
+#endif
+static struct vio_dev vio_bus_device  = { /* fake "parent" device */
+	.name = vio_bus_device.dev.bus_id,
+	.type = "",
+#ifdef CONFIG_PPC_ISERIES
+	.iommu_table = &vio_iommu_table,
+#endif
+	.dev.bus_id = "vio",
+	.dev.bus = &vio_bus_type,
+};
 
 #ifdef CONFIG_PPC_ISERIES
 static struct vio_dev *__init vio_register_device_iseries(char *type,
 		uint32_t unit_num);
 
-static struct iommu_table veth_iommu_table;
-static struct iommu_table vio_iommu_table;
-
-static struct vio_dev _vio_dev  = {
-	.iommu_table = &vio_iommu_table,
-	.dev.bus = &vio_bus_type
-};
-struct device *iSeries_vio_dev = &_vio_dev.dev;
+struct device *iSeries_vio_dev = &vio_bus_device.dev;
 EXPORT_SYMBOL(iSeries_vio_dev);
 
 #define device_is_compatible(a, b)	1
@@ -260,18 +265,10 @@
 	}
 
 	/* the fake parent of all vio devices, just to give us a nice directory */
-	vio_bus_device = kmalloc(sizeof(struct vio_dev), GFP_KERNEL);
-	if (!vio_bus_device) {
-		return 1;
-	}
-	memset(vio_bus_device, 0, sizeof(struct vio_dev));
-	strcpy(vio_bus_device->dev.bus_id, "vio");
-
-	err = device_register(&vio_bus_device->dev);
+	err = device_register(&vio_bus_device.dev);
 	if (err) {
 		printk(KERN_WARNING "%s: device_register returned %i\n", __FUNCTION__,
 			err);
-		kfree(vio_bus_device);
 		return err;
 	}
 
@@ -326,7 +323,7 @@
 	viodev->unit_address = unit_address;
 	viodev->iommu_table = iommu_table;
 	/* init generic 'struct device' fields: */
-	viodev->dev.parent = &vio_bus_device->dev;
+	viodev->dev.parent = &vio_bus_device.dev;
 	viodev->dev.bus = &vio_bus_type;
 	viodev->dev.release = vio_dev_release;
 
@@ -636,5 +633,3 @@
 	.name = "vio",
 	.match = vio_bus_match,
 };
-
-EXPORT_SYMBOL(vio_bus_type);
diff --git a/arch/ppc64/kernel/viopath.c b/arch/ppc64/kernel/viopath.c
index 2ed8ee0..2a6c4f0 100644
--- a/arch/ppc64/kernel/viopath.c
+++ b/arch/ppc64/kernel/viopath.c
@@ -43,12 +43,10 @@
 #include <asm/system.h>
 #include <asm/uaccess.h>
 #include <asm/iSeries/HvTypes.h>
-#include <asm/iSeries/LparData.h>
+#include <asm/iSeries/ItExtVpdPanel.h>
 #include <asm/iSeries/HvLpEvent.h>
 #include <asm/iSeries/HvLpConfig.h>
-#include <asm/iSeries/HvCallCfg.h>
 #include <asm/iSeries/mf.h>
-#include <asm/iSeries/iSeries_proc.h>
 #include <asm/iSeries/vio.h>
 
 /* Status of the path to each other partition in the system.
@@ -365,7 +363,7 @@
 	 * while we're active
 	 */
 	viopath_ourLp = HvLpConfig_getLpIndex();
-	viopath_hostLp = HvCallCfg_getHostingLpIndex(viopath_ourLp);
+	viopath_hostLp = HvLpConfig_getHostingLpIndex(viopath_ourLp);
 
 	if (viopath_hostLp != HvLpIndexInvalid)
 		vio_setHandler(viomajorsubtype_config, handleConfig);
@@ -487,7 +485,7 @@
 	unsigned long flags;
 	int tempNumAllocated;
 
-	if ((remoteLp >= HvMaxArchitectedLps) || (remoteLp == HvLpIndexInvalid))
+	if ((remoteLp >= HVMAXARCHITECTEDLPS) || (remoteLp == HvLpIndexInvalid))
 		return -EINVAL;
 
 	subtype = subtype >> VIOMAJOR_SUBTYPE_SHIFT;
@@ -558,7 +556,7 @@
 	int numOpen;
 	struct alloc_parms parms;
 
-	if ((remoteLp >= HvMaxArchitectedLps) || (remoteLp == HvLpIndexInvalid))
+	if ((remoteLp >= HVMAXARCHITECTEDLPS) || (remoteLp == HvLpIndexInvalid))
 		return -EINVAL;
 
 	subtype = subtype >> VIOMAJOR_SUBTYPE_SHIFT;
diff --git a/arch/ppc64/lib/Makefile b/arch/ppc64/lib/Makefile
index bf7b5bb..76fbfa9 100644
--- a/arch/ppc64/lib/Makefile
+++ b/arch/ppc64/lib/Makefile
@@ -12,7 +12,7 @@
 
 # e2a provides EBCDIC to ASCII conversions.
 ifdef CONFIG_PPC_ISERIES
-obj-$(CONFIG_PCI)	+= e2a.o
+obj-y += e2a.o
 endif
 
 lib-$(CONFIG_DEBUG_KERNEL) += sstep.o
diff --git a/arch/ppc64/mm/hash_utils.c b/arch/ppc64/mm/hash_utils.c
index 0a0f970..1647b1c 100644
--- a/arch/ppc64/mm/hash_utils.c
+++ b/arch/ppc64/mm/hash_utils.c
@@ -195,7 +195,7 @@
 		memset((void *)table, 0, htab_size_bytes);
 	}
 
-	mode_rw = _PAGE_ACCESSED | _PAGE_COHERENT | PP_RWXX;
+	mode_rw = _PAGE_ACCESSED | _PAGE_DIRTY | _PAGE_COHERENT | PP_RWXX;
 
 	/* On U3 based machines, we need to reserve the DART area and
 	 * _NOT_ map it to avoid cache paradoxes as it's remapped non
@@ -310,10 +310,6 @@
 
 		vsid = get_vsid(mm->context.id, ea);
 		break;
-	case IO_REGION_ID:
-		mm = &ioremap_mm;
-		vsid = get_kernel_vsid(ea);
-		break;
 	case VMALLOC_REGION_ID:
 		mm = &init_mm;
 		vsid = get_kernel_vsid(ea);
diff --git a/arch/ppc64/mm/hugetlbpage.c b/arch/ppc64/mm/hugetlbpage.c
index d3bf86a..fdcfe97 100644
--- a/arch/ppc64/mm/hugetlbpage.c
+++ b/arch/ppc64/mm/hugetlbpage.c
@@ -121,7 +121,7 @@
 	return hugepte_offset(dir, addr);
 }
 
-static pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
 {
 	pud_t *pud;
 
@@ -134,7 +134,7 @@
 	return hugepte_offset(pud, addr);
 }
 
-static pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
 {
 	pud_t *pud;
 
@@ -147,25 +147,6 @@
 	return hugepte_alloc(mm, pud, addr);
 }
 
-static void set_huge_pte(struct mm_struct *mm, struct vm_area_struct *vma,
-			 unsigned long addr, struct page *page,
-			 pte_t *ptep, int write_access)
-{
-	pte_t entry;
-
-	add_mm_counter(mm, rss, HPAGE_SIZE / PAGE_SIZE);
-	if (write_access) {
-		entry =
-		    pte_mkwrite(pte_mkdirty(mk_pte(page, vma->vm_page_prot)));
-	} else {
-		entry = pte_wrprotect(mk_pte(page, vma->vm_page_prot));
-	}
-	entry = pte_mkyoung(entry);
-	entry = pte_mkhuge(entry);
-
-	set_pte_at(mm, addr, ptep, entry);
-}
-
 /*
  * This function checks for proper alignment of input addr and len parameters.
  */
@@ -259,80 +240,6 @@
 	return -EINVAL;
 }
 
-int copy_hugetlb_page_range(struct mm_struct *dst, struct mm_struct *src,
-			struct vm_area_struct *vma)
-{
-	pte_t *src_pte, *dst_pte, entry;
-	struct page *ptepage;
-	unsigned long addr = vma->vm_start;
-	unsigned long end = vma->vm_end;
-	int err = -ENOMEM;
-
-	while (addr < end) {
-		dst_pte = huge_pte_alloc(dst, addr);
-		if (!dst_pte)
-			goto out;
-
-		src_pte = huge_pte_offset(src, addr);
-		entry = *src_pte;
-		
-		ptepage = pte_page(entry);
-		get_page(ptepage);
-		add_mm_counter(dst, rss, HPAGE_SIZE / PAGE_SIZE);
-		set_pte_at(dst, addr, dst_pte, entry);
-
-		addr += HPAGE_SIZE;
-	}
-
-	err = 0;
- out:
-	return err;
-}
-
-int
-follow_hugetlb_page(struct mm_struct *mm, struct vm_area_struct *vma,
-		    struct page **pages, struct vm_area_struct **vmas,
-		    unsigned long *position, int *length, int i)
-{
-	unsigned long vpfn, vaddr = *position;
-	int remainder = *length;
-
-	WARN_ON(!is_vm_hugetlb_page(vma));
-
-	vpfn = vaddr/PAGE_SIZE;
-	while (vaddr < vma->vm_end && remainder) {
-		if (pages) {
-			pte_t *pte;
-			struct page *page;
-
-			pte = huge_pte_offset(mm, vaddr);
-
-			/* hugetlb should be locked, and hence, prefaulted */
-			WARN_ON(!pte || pte_none(*pte));
-
-			page = &pte_page(*pte)[vpfn % (HPAGE_SIZE/PAGE_SIZE)];
-
-			WARN_ON(!PageCompound(page));
-
-			get_page(page);
-			pages[i] = page;
-		}
-
-		if (vmas)
-			vmas[i] = vma;
-
-		vaddr += PAGE_SIZE;
-		++vpfn;
-		--remainder;
-		++i;
-	}
-
-	*length = remainder;
-	*position = vaddr;
-
-	return i;
-}
-
 struct page *
 follow_huge_addr(struct mm_struct *mm, unsigned long address, int write)
 {
@@ -363,89 +270,6 @@
 	return NULL;
 }
 
-void unmap_hugepage_range(struct vm_area_struct *vma,
-			  unsigned long start, unsigned long end)
-{
-	struct mm_struct *mm = vma->vm_mm;
-	unsigned long addr;
-	pte_t *ptep;
-	struct page *page;
-
-	WARN_ON(!is_vm_hugetlb_page(vma));
-	BUG_ON((start % HPAGE_SIZE) != 0);
-	BUG_ON((end % HPAGE_SIZE) != 0);
-
-	for (addr = start; addr < end; addr += HPAGE_SIZE) {
-		pte_t pte;
-
-		ptep = huge_pte_offset(mm, addr);
-		if (!ptep || pte_none(*ptep))
-			continue;
-
-		pte = *ptep;
-		page = pte_page(pte);
-		pte_clear(mm, addr, ptep);
-
-		put_page(page);
-	}
-	add_mm_counter(mm, rss, -((end - start) >> PAGE_SHIFT));
-	flush_tlb_pending();
-}
-
-int hugetlb_prefault(struct address_space *mapping, struct vm_area_struct *vma)
-{
-	struct mm_struct *mm = current->mm;
-	unsigned long addr;
-	int ret = 0;
-
-	WARN_ON(!is_vm_hugetlb_page(vma));
-	BUG_ON((vma->vm_start % HPAGE_SIZE) != 0);
-	BUG_ON((vma->vm_end % HPAGE_SIZE) != 0);
-
-	spin_lock(&mm->page_table_lock);
-	for (addr = vma->vm_start; addr < vma->vm_end; addr += HPAGE_SIZE) {
-		unsigned long idx;
-		pte_t *pte = huge_pte_alloc(mm, addr);
-		struct page *page;
-
-		if (!pte) {
-			ret = -ENOMEM;
-			goto out;
-		}
-		if (! pte_none(*pte))
-			continue;
-
-		idx = ((addr - vma->vm_start) >> HPAGE_SHIFT)
-			+ (vma->vm_pgoff >> (HPAGE_SHIFT - PAGE_SHIFT));
-		page = find_get_page(mapping, idx);
-		if (!page) {
-			/* charge the fs quota first */
-			if (hugetlb_get_quota(mapping)) {
-				ret = -ENOMEM;
-				goto out;
-			}
-			page = alloc_huge_page();
-			if (!page) {
-				hugetlb_put_quota(mapping);
-				ret = -ENOMEM;
-				goto out;
-			}
-			ret = add_to_page_cache(page, mapping, idx, GFP_ATOMIC);
-			if (! ret) {
-				unlock_page(page);
-			} else {
-				hugetlb_put_quota(mapping);
-				free_huge_page(page);
-				goto out;
-			}
-		}
-		set_huge_pte(mm, vma, addr, page, pte, vma->vm_flags & VM_WRITE);
-	}
-out:
-	spin_unlock(&mm->page_table_lock);
-	return ret;
-}
-
 /* Because we have an exclusive hugepage region which lies within the
  * normal user address space, we have to take special measures to make
  * non-huge mmap()s evade the hugepage reserved regions. */
@@ -468,7 +292,12 @@
 		    && !is_hugepage_only_range(mm, addr,len))
 			return addr;
 	}
-	start_addr = addr = mm->free_area_cache;
+	if (len > mm->cached_hole_size) {
+	        start_addr = addr = mm->free_area_cache;
+	} else {
+	        start_addr = addr = TASK_UNMAPPED_BASE;
+	        mm->cached_hole_size = 0;
+	}
 
 full_search:
 	vma = find_vma(mm, addr);
@@ -492,6 +321,8 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
 		addr = vma->vm_end;
 		vma = vma->vm_next;
 	}
@@ -499,6 +330,7 @@
 	/* Make sure we didn't miss any holes */
 	if (start_addr != TASK_UNMAPPED_BASE) {
 		start_addr = addr = TASK_UNMAPPED_BASE;
+		mm->cached_hole_size = 0;
 		goto full_search;
 	}
 	return -ENOMEM;
@@ -520,6 +352,7 @@
 	struct vm_area_struct *vma, *prev_vma;
 	struct mm_struct *mm = current->mm;
 	unsigned long base = mm->mmap_base, addr = addr0;
+	unsigned long largest_hole = mm->cached_hole_size;
 	int first_time = 1;
 
 	/* requested length too big for entire address space */
@@ -540,6 +373,10 @@
 			return addr;
 	}
 
+	if (len <= largest_hole) {
+	        largest_hole = 0;
+		mm->free_area_cache = base;
+	}
 try_again:
 	/* make sure it can fit in the remaining address space */
 	if (mm->free_area_cache < len)
@@ -568,13 +405,21 @@
 		 * vma->vm_start, use it:
 		 */
 		if (addr+len <= vma->vm_start &&
-				(!prev_vma || (addr >= prev_vma->vm_end)))
+		          (!prev_vma || (addr >= prev_vma->vm_end))) {
 			/* remember the address as a hint for next time */
-			return (mm->free_area_cache = addr);
-		else
+		        mm->cached_hole_size = largest_hole;
+		        return (mm->free_area_cache = addr);
+		} else {
 			/* pull free_area_cache down to the first hole */
-			if (mm->free_area_cache == vma->vm_end)
+		        if (mm->free_area_cache == vma->vm_end) {
 				mm->free_area_cache = vma->vm_start;
+				mm->cached_hole_size = largest_hole;
+			}
+		}
+
+		/* remember the largest hole we saw so far */
+		if (addr + largest_hole < vma->vm_start)
+		        largest_hole = vma->vm_start - addr;
 
 		/* try just below the current vma->vm_start */
 		addr = vma->vm_start-len;
@@ -587,6 +432,7 @@
 	 */
 	if (first_time) {
 		mm->free_area_cache = base;
+		largest_hole = 0;
 		first_time = 0;
 		goto try_again;
 	}
@@ -597,11 +443,13 @@
 	 * allocations.
 	 */
 	mm->free_area_cache = TASK_UNMAPPED_BASE;
+	mm->cached_hole_size = ~0UL;
 	addr = arch_get_unmapped_area(filp, addr0, len, pgoff, flags);
 	/*
 	 * Restore the topdown base:
 	 */
 	mm->free_area_cache = base;
+	mm->cached_hole_size = ~0UL;
 
 	return addr;
 }
diff --git a/arch/ppc64/mm/imalloc.c b/arch/ppc64/mm/imalloc.c
index cb8727f..b6e75b8 100644
--- a/arch/ppc64/mm/imalloc.c
+++ b/arch/ppc64/mm/imalloc.c
@@ -15,6 +15,7 @@
 #include <asm/pgtable.h>
 #include <asm/semaphore.h>
 #include <asm/imalloc.h>
+#include <asm/cacheflush.h>
 
 static DECLARE_MUTEX(imlist_sem);
 struct vm_struct * imlist = NULL;
@@ -285,29 +286,32 @@
 	return area;
 }
 
-unsigned long im_free(void * addr)
+void im_free(void * addr)
 {
 	struct vm_struct **p, *tmp;
-	unsigned long ret_size = 0;
   
 	if (!addr)
-		return ret_size;
-	if ((PAGE_SIZE-1) & (unsigned long) addr) {
+		return;
+	if ((unsigned long) addr & ~PAGE_MASK) {
 		printk(KERN_ERR "Trying to %s bad address (%p)\n", __FUNCTION__,			addr);
-		return ret_size;
+		return;
 	}
 	down(&imlist_sem);
 	for (p = &imlist ; (tmp = *p) ; p = &tmp->next) {
 		if (tmp->addr == addr) {
-			ret_size = tmp->size;
 			*p = tmp->next;
+
+			/* XXX: do we need the lock? */
+			spin_lock(&init_mm.page_table_lock);
+			unmap_vm_area(tmp);
+			spin_unlock(&init_mm.page_table_lock);
+
 			kfree(tmp);
 			up(&imlist_sem);
-			return ret_size;
+			return;
 		}
 	}
 	up(&imlist_sem);
 	printk(KERN_ERR "Trying to %s nonexistent area (%p)\n", __FUNCTION__,
 			addr);
-	return ret_size;
 }
diff --git a/arch/ppc64/mm/init.c b/arch/ppc64/mm/init.c
index 4b42aff..6fa1e64 100644
--- a/arch/ppc64/mm/init.c
+++ b/arch/ppc64/mm/init.c
@@ -73,9 +73,6 @@
 extern pgd_t swapper_pg_dir[];
 extern struct task_struct *current_set[NR_CPUS];
 
-extern pgd_t ioremap_dir[];
-pgd_t * ioremap_pgd = (pgd_t *)&ioremap_dir;
-
 unsigned long klimit = (unsigned long)_end;
 
 unsigned long _SDR1=0;
@@ -137,69 +134,6 @@
 
 #else
 
-static void unmap_im_area_pte(pmd_t *pmd, unsigned long addr,
-				  unsigned long end)
-{
-	pte_t *pte;
-
-	pte = pte_offset_kernel(pmd, addr);
-	do {
-		pte_t ptent = ptep_get_and_clear(&ioremap_mm, addr, pte);
-		WARN_ON(!pte_none(ptent) && !pte_present(ptent));
-	} while (pte++, addr += PAGE_SIZE, addr != end);
-}
-
-static inline void unmap_im_area_pmd(pud_t *pud, unsigned long addr,
-				     unsigned long end)
-{
-	pmd_t *pmd;
-	unsigned long next;
-
-	pmd = pmd_offset(pud, addr);
-	do {
-		next = pmd_addr_end(addr, end);
-		if (pmd_none_or_clear_bad(pmd))
-			continue;
-		unmap_im_area_pte(pmd, addr, next);
-	} while (pmd++, addr = next, addr != end);
-}
-
-static inline void unmap_im_area_pud(pgd_t *pgd, unsigned long addr,
-				     unsigned long end)
-{
-	pud_t *pud;
-	unsigned long next;
-
-	pud = pud_offset(pgd, addr);
-	do {
-		next = pud_addr_end(addr, end);
-		if (pud_none_or_clear_bad(pud))
-			continue;
-		unmap_im_area_pmd(pud, addr, next);
-	} while (pud++, addr = next, addr != end);
-}
-
-static void unmap_im_area(unsigned long addr, unsigned long end)
-{
-	struct mm_struct *mm = &ioremap_mm;
-	unsigned long next;
-	pgd_t *pgd;
-
-	spin_lock(&mm->page_table_lock);
-
-	pgd = pgd_offset_i(addr);
-	flush_cache_vunmap(addr, end);
-	do {
-		next = pgd_addr_end(addr, end);
-		if (pgd_none_or_clear_bad(pgd))
-			continue;
-		unmap_im_area_pud(pgd, addr, next);
-	} while (pgd++, addr = next, addr != end);
-	flush_tlb_kernel_range(start, end);
-
-	spin_unlock(&mm->page_table_lock);
-}
-
 /*
  * map_io_page currently only called by __ioremap
  * map_io_page adds an entry to the ioremap page table
@@ -214,21 +148,21 @@
 	unsigned long vsid;
 
 	if (mem_init_done) {
-		spin_lock(&ioremap_mm.page_table_lock);
-		pgdp = pgd_offset_i(ea);
-		pudp = pud_alloc(&ioremap_mm, pgdp, ea);
+		spin_lock(&init_mm.page_table_lock);
+		pgdp = pgd_offset_k(ea);
+		pudp = pud_alloc(&init_mm, pgdp, ea);
 		if (!pudp)
 			return -ENOMEM;
-		pmdp = pmd_alloc(&ioremap_mm, pudp, ea);
+		pmdp = pmd_alloc(&init_mm, pudp, ea);
 		if (!pmdp)
 			return -ENOMEM;
-		ptep = pte_alloc_kernel(&ioremap_mm, pmdp, ea);
+		ptep = pte_alloc_kernel(&init_mm, pmdp, ea);
 		if (!ptep)
 			return -ENOMEM;
 		pa = abs_to_phys(pa);
-		set_pte_at(&ioremap_mm, ea, ptep, pfn_pte(pa >> PAGE_SHIFT,
+		set_pte_at(&init_mm, ea, ptep, pfn_pte(pa >> PAGE_SHIFT,
 							  __pgprot(flags)));
-		spin_unlock(&ioremap_mm.page_table_lock);
+		spin_unlock(&init_mm.page_table_lock);
 	} else {
 		unsigned long va, vpn, hash, hpteg;
 
@@ -267,13 +201,9 @@
 
 	for (i = 0; i < size; i += PAGE_SIZE)
 		if (map_io_page(ea+i, pa+i, flags))
-			goto failure;
+			return NULL;
 
 	return (void __iomem *) (ea + (addr & ~PAGE_MASK));
- failure:
-	if (mem_init_done)
-		unmap_im_area(ea, ea + size);
-	return NULL;
 }
 
 
@@ -381,19 +311,14 @@
  */
 void iounmap(volatile void __iomem *token)
 {
-	unsigned long address, size;
 	void *addr;
 
 	if (!mem_init_done)
 		return;
 	
 	addr = (void *) ((unsigned long __force) token & PAGE_MASK);
-	
-	if ((size = im_free(addr)) == 0)
-		return;
 
-	address = (unsigned long)addr; 
-	unmap_im_area(address, address + size);
+	im_free(addr);
 }
 
 static int iounmap_subset_regions(unsigned long addr, unsigned long size)
diff --git a/arch/ppc64/xmon/xmon.c b/arch/ppc64/xmon/xmon.c
index 3c0ccb2..7f6e13a 100644
--- a/arch/ppc64/xmon/xmon.c
+++ b/arch/ppc64/xmon/xmon.c
@@ -2247,7 +2247,14 @@
 			tmpstr[i] = c;
 		}
 		tmpstr[i++] = 0;
-		*vp = kallsyms_lookup_name(tmpstr);
+		*vp = 0;
+		if (setjmp(bus_error_jmp) == 0) {
+			catch_memory_errors = 1;
+			sync();
+			*vp = kallsyms_lookup_name(tmpstr);
+			sync();
+		}
+		catch_memory_errors = 0;
 		if (!(*vp)) {
 			printf("unknown symbol '%s'\n", tmpstr);
 			return 0;
diff --git a/arch/s390/kernel/compat_ioctl.c b/arch/s390/kernel/compat_ioctl.c
index 03d03c6..24a1e9f 100644
--- a/arch/s390/kernel/compat_ioctl.c
+++ b/arch/s390/kernel/compat_ioctl.c
@@ -42,7 +42,6 @@
 #include "../../../fs/compat_ioctl.c"
 
 /* s390 only ioctls */
-#if defined(CONFIG_DASD) || defined(CONFIG_DASD_MODULE)
 COMPATIBLE_IOCTL(DASDAPIVER)
 COMPATIBLE_IOCTL(BIODASDDISABLE)
 COMPATIBLE_IOCTL(BIODASDENABLE)
@@ -59,16 +58,11 @@
 COMPATIBLE_IOCTL(BIODASDPSRD)
 COMPATIBLE_IOCTL(BIODASDGATTR)
 COMPATIBLE_IOCTL(BIODASDSATTR)
-#if defined(CONFIG_DASD_CMB) || defined(CONFIG_DASD_CMB_MODULE)
 COMPATIBLE_IOCTL(BIODASDCMFENABLE)
 COMPATIBLE_IOCTL(BIODASDCMFDISABLE)
 COMPATIBLE_IOCTL(BIODASDREADALLCMB)
-#endif
-#endif
 
-#if defined(CONFIG_S390_TAPE) || defined(CONFIG_S390_TAPE_MODULE)
 COMPATIBLE_IOCTL(TAPE390_DISPLAY)
-#endif
 
 /* s390 doesn't need handlers here */
 COMPATIBLE_IOCTL(TIOCGSERIAL)
diff --git a/arch/s390/kernel/head.S b/arch/s390/kernel/head.S
index b804c55..fc8bf5e 100644
--- a/arch/s390/kernel/head.S
+++ b/arch/s390/kernel/head.S
@@ -345,10 +345,25 @@
 	bno   .Lnoreset
         la    %r2,.Lreset              
         lhi   %r3,26
-        .long 0x83230008
+	diag  %r2,%r3,8
+	mvc   0x78(8),.Lrdrnewpsw              # set up IO interrupt psw
+.Lwaitrdrirq:
+	lpsw  .Lrdrwaitpsw
+.Lrdrint:
+	c     %r1,0xb8                         # compare subchannel number
+	bne   .Lwaitrdrirq
+	la    %r5,.Lirb
+	tsch  0(%r5)
 .Lnoreset:
+        b     .Lnoload
+
+	.align 8
+.Lrdrnewpsw:
+	.long  0x00080000,0x80000000+.Lrdrint
+.Lrdrwaitpsw:
+	.long  0x020a0000,0x80000000+.Lrdrint
 #endif
-	
+
 #
 # everything loaded, go for it
 #
@@ -517,10 +532,10 @@
 	l     %r2, .Lrcp2-.LPG1(%r13)	# try with Read SCP
 	b     .Lservicecall-.LPG1(%r13)
 .Lprocsccb:
-	lh    %r1,.Lscpincr1-PARMAREA(%r4) # use this one if != 0
-	chi   %r1,0x00
-	jne   .Lscnd
-	l     %r1,.Lscpincr2-PARMAREA(%r4) # otherwise use this one
+	lhi   %r1,0
+	icm   %r1,3,.Lscpincr1-PARMAREA(%r4) # use this one if != 0
+	jnz   .Lscnd
+	l     %r1,.Lscpincr2-PARMAREA+4(%r4) # otherwise use this one
 .Lscnd:
 	xr    %r3,%r3			# same logic
 	ic    %r3,.Lscpa1-PARMAREA(%r4)
diff --git a/arch/s390/kernel/head64.S b/arch/s390/kernel/head64.S
index 8366793..f525c0c 100644
--- a/arch/s390/kernel/head64.S
+++ b/arch/s390/kernel/head64.S
@@ -344,10 +344,25 @@
 	bno   .Lnoreset
         la    %r2,.Lreset              
         lhi   %r3,26
-        .long 0x83230008
+	diag  %r2,%r3,8
+	mvc   0x78(8),.Lrdrnewpsw	       # set up IO interrupt psw
+.Lwaitrdrirq:
+	lpsw  .Lrdrwaitpsw
+.Lrdrint:
+	c     %r1,0xb8			       # compare subchannel number
+	bne   .Lwaitrdrirq
+	la    %r5,.Lirb
+	tsch  0(%r5)
 .Lnoreset:
+	b     .Lnoload
+
+	.align 8
+.Lrdrnewpsw:
+	.long  0x00080000,0x80000000+.Lrdrint
+.Lrdrwaitpsw:
+	.long  0x020a0000,0x80000000+.Lrdrint
 #endif
-	
+
 #
 # everything loaded, go for it
 #
@@ -518,9 +533,9 @@
 	l     %r2,.Lrcp2-.LPG1(%r13)	# try with Read SCP
 	b     .Lservicecall-.LPG1(%r13)
 .Lprocsccb:
-	lh    %r1,.Lscpincr1-PARMAREA(%r4) # use this one if != 0
-	chi   %r1,0x00
-	jne   .Lscnd
+	lghi  %r1,0
+	icm   %r1,3,.Lscpincr1-PARMAREA(%r4) # use this one if != 0
+	jnz   .Lscnd
 	lg    %r1,.Lscpincr2-PARMAREA(%r4) # otherwise use this one
 .Lscnd:
 	xr    %r3,%r3			# same logic
diff --git a/arch/s390/kernel/traps.c b/arch/s390/kernel/traps.c
index 8b90e95..ca34b6f 100644
--- a/arch/s390/kernel/traps.c
+++ b/arch/s390/kernel/traps.c
@@ -668,7 +668,10 @@
 
 asmlinkage void kernel_stack_overflow(struct pt_regs * regs)
 {
-	die("Kernel stack overflow", regs, 0);
+	bust_spinlocks(1);
+	printk("Kernel stack overflow.\n");
+	show_regs(regs);
+	bust_spinlocks(0);
 	panic("Corrupt kernel stack, can't continue.");
 }
 
diff --git a/arch/s390/mm/cmm.c b/arch/s390/mm/cmm.c
index f5a5bc0..2d5cb13 100644
--- a/arch/s390/mm/cmm.c
+++ b/arch/s390/mm/cmm.c
@@ -21,7 +21,7 @@
 #include <asm/uaccess.h>
 
 static char *sender = "VMRMSVM";
-module_param(sender, charp, 0);
+module_param(sender, charp, 0400);
 MODULE_PARM_DESC(sender,
 		 "Guest name that may send SMSG messages (default VMRMSVM)");
 
diff --git a/arch/sh/kernel/sys_sh.c b/arch/sh/kernel/sys_sh.c
index df5ac29..917b2f3 100644
--- a/arch/sh/kernel/sys_sh.c
+++ b/arch/sh/kernel/sys_sh.c
@@ -79,6 +79,10 @@
 		    (!vma || addr + len <= vma->vm_start))
 			return addr;
 	}
+	if (len <= mm->cached_hole_size) {
+	        mm->cached_hole_size = 0;
+		mm->free_area_cache = TASK_UNMAPPED_BASE;
+	}
 	if (flags & MAP_PRIVATE)
 		addr = PAGE_ALIGN(mm->free_area_cache);
 	else
@@ -95,6 +99,7 @@
 			 */
 			if (start_addr != TASK_UNMAPPED_BASE) {
 				start_addr = addr = TASK_UNMAPPED_BASE;
+				mm->cached_hole_size = 0;
 				goto full_search;
 			}
 			return -ENOMEM;
@@ -106,6 +111,9 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
+
 		addr = vma->vm_end;
 		if (!(flags & MAP_PRIVATE))
 			addr = COLOUR_ALIGN(addr);
diff --git a/arch/sh/lib/delay.c b/arch/sh/lib/delay.c
index 50b3603..3517146 100644
--- a/arch/sh/lib/delay.c
+++ b/arch/sh/lib/delay.c
@@ -24,7 +24,7 @@
 	__asm__("dmulu.l	%0, %2\n\t"
 		"sts	mach, %0"
 		: "=r" (xloops)
-		: "0" (xloops), "r" (cpu_data[_smp_processor_id()].loops_per_jiffy)
+		: "0" (xloops), "r" (cpu_data[raw_smp_processor_id()].loops_per_jiffy)
 		: "macl", "mach");
 	__delay(xloops * HZ);
 }
diff --git a/arch/sh/mm/hugetlbpage.c b/arch/sh/mm/hugetlbpage.c
index 1f897ba..95bb1a6 100644
--- a/arch/sh/mm/hugetlbpage.c
+++ b/arch/sh/mm/hugetlbpage.c
@@ -24,7 +24,7 @@
 #include <asm/tlbflush.h>
 #include <asm/cacheflush.h>
 
-static pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pmd_t *pmd;
@@ -39,7 +39,7 @@
 	return pte;
 }
 
-static pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pmd_t *pmd;
@@ -56,30 +56,36 @@
 
 #define mk_pte_huge(entry) do { pte_val(entry) |= _PAGE_SZHUGE; } while (0)
 
-static void set_huge_pte(struct mm_struct *mm, struct vm_area_struct *vma,
-			 struct page *page, pte_t * page_table, int write_access)
+void set_huge_pte_at(struct mm_struct *mm, unsigned long addr,
+		     pte_t *ptep, pte_t entry)
 {
-	unsigned long i;
-	pte_t entry;
-
-	add_mm_counter(mm, rss, HPAGE_SIZE / PAGE_SIZE);
-
-	if (write_access)
-		entry = pte_mkwrite(pte_mkdirty(mk_pte(page,
-						       vma->vm_page_prot)));
-	else
-		entry = pte_wrprotect(mk_pte(page, vma->vm_page_prot));
-	entry = pte_mkyoung(entry);
-	mk_pte_huge(entry);
+	int i;
 
 	for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
-		set_pte(page_table, entry);
-		page_table++;
-
+		set_pte_at(mm, addr, ptep, entry);
+		ptep++;
+		addr += PAGE_SIZE;
 		pte_val(entry) += PAGE_SIZE;
 	}
 }
 
+pte_t huge_ptep_get_and_clear(struct mm_struct *mm, unsigned long addr,
+			      pte_t *ptep)
+{
+	pte_t entry;
+	int i;
+
+	entry = *ptep;
+
+	for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
+		pte_clear(mm, addr, ptep);
+		addr += PAGE_SIZE;
+		ptep++;
+	}
+
+	return entry;
+}
+
 /*
  * This function checks for proper alignment of input addr and len parameters.
  */
@@ -92,79 +98,6 @@
 	return 0;
 }
 
-int copy_hugetlb_page_range(struct mm_struct *dst, struct mm_struct *src,
-			    struct vm_area_struct *vma)
-{
-	pte_t *src_pte, *dst_pte, entry;
-	struct page *ptepage;
-	unsigned long addr = vma->vm_start;
-	unsigned long end = vma->vm_end;
-	int i;
-
-	while (addr < end) {
-		dst_pte = huge_pte_alloc(dst, addr);
-		if (!dst_pte)
-			goto nomem;
-		src_pte = huge_pte_offset(src, addr);
-		BUG_ON(!src_pte || pte_none(*src_pte));
-		entry = *src_pte;
-		ptepage = pte_page(entry);
-		get_page(ptepage);
-		for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
-			set_pte(dst_pte, entry);
-			pte_val(entry) += PAGE_SIZE;
-			dst_pte++;
-		}
-		add_mm_counter(dst, rss, HPAGE_SIZE / PAGE_SIZE);
-		addr += HPAGE_SIZE;
-	}
-	return 0;
-
-nomem:
-	return -ENOMEM;
-}
-
-int follow_hugetlb_page(struct mm_struct *mm, struct vm_area_struct *vma,
-			struct page **pages, struct vm_area_struct **vmas,
-			unsigned long *position, int *length, int i)
-{
-	unsigned long vaddr = *position;
-	int remainder = *length;
-
-	WARN_ON(!is_vm_hugetlb_page(vma));
-
-	while (vaddr < vma->vm_end && remainder) {
-		if (pages) {
-			pte_t *pte;
-			struct page *page;
-
-			pte = huge_pte_offset(mm, vaddr);
-
-			/* hugetlb should be locked, and hence, prefaulted */
-			BUG_ON(!pte || pte_none(*pte));
-
-			page = pte_page(*pte);
-
-			WARN_ON(!PageCompound(page));
-
-			get_page(page);
-			pages[i] = page;
-		}
-
-		if (vmas)
-			vmas[i] = vma;
-
-		vaddr += PAGE_SIZE;
-		--remainder;
-		++i;
-	}
-
-	*length = remainder;
-	*position = vaddr;
-
-	return i;
-}
-
 struct page *follow_huge_addr(struct mm_struct *mm,
 			      unsigned long address, int write)
 {
@@ -181,84 +114,3 @@
 {
 	return NULL;
 }
-
-void unmap_hugepage_range(struct vm_area_struct *vma,
-			  unsigned long start, unsigned long end)
-{
-	struct mm_struct *mm = vma->vm_mm;
-	unsigned long address;
-	pte_t *pte;
-	struct page *page;
-	int i;
-
-	BUG_ON(start & (HPAGE_SIZE - 1));
-	BUG_ON(end & (HPAGE_SIZE - 1));
-
-	for (address = start; address < end; address += HPAGE_SIZE) {
-		pte = huge_pte_offset(mm, address);
-		BUG_ON(!pte);
-		if (pte_none(*pte))
-			continue;
-		page = pte_page(*pte);
-		put_page(page);
-		for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
-			pte_clear(mm, address+(i*PAGE_SIZE), pte);
-			pte++;
-		}
-	}
-	add_mm_counter(mm, rss, -((end - start) >> PAGE_SHIFT));
-	flush_tlb_range(vma, start, end);
-}
-
-int hugetlb_prefault(struct address_space *mapping, struct vm_area_struct *vma)
-{
-	struct mm_struct *mm = current->mm;
-	unsigned long addr;
-	int ret = 0;
-
-	BUG_ON(vma->vm_start & ~HPAGE_MASK);
-	BUG_ON(vma->vm_end & ~HPAGE_MASK);
-
-	spin_lock(&mm->page_table_lock);
-	for (addr = vma->vm_start; addr < vma->vm_end; addr += HPAGE_SIZE) {
-		unsigned long idx;
-		pte_t *pte = huge_pte_alloc(mm, addr);
-		struct page *page;
-
-		if (!pte) {
-			ret = -ENOMEM;
-			goto out;
-		}
-		if (!pte_none(*pte))
-			continue;
-
-		idx = ((addr - vma->vm_start) >> HPAGE_SHIFT)
-			+ (vma->vm_pgoff >> (HPAGE_SHIFT - PAGE_SHIFT));
-		page = find_get_page(mapping, idx);
-		if (!page) {
-			/* charge the fs quota first */
-			if (hugetlb_get_quota(mapping)) {
-				ret = -ENOMEM;
-				goto out;
-			}
-			page = alloc_huge_page();
-			if (!page) {
-				hugetlb_put_quota(mapping);
-				ret = -ENOMEM;
-				goto out;
-			}
-			ret = add_to_page_cache(page, mapping, idx, GFP_ATOMIC);
-			if (! ret) {
-				unlock_page(page);
-			} else {
-				hugetlb_put_quota(mapping);
-				free_huge_page(page);
-				goto out;
-			}
-		}
-		set_huge_pte(mm, vma, page, pte, vma->vm_flags & VM_WRITE);
-	}
-out:
-	spin_unlock(&mm->page_table_lock);
-	return ret;
-}
diff --git a/arch/sh64/mm/hugetlbpage.c b/arch/sh64/mm/hugetlbpage.c
index bcad2ae..dcd9c8a 100644
--- a/arch/sh64/mm/hugetlbpage.c
+++ b/arch/sh64/mm/hugetlbpage.c
@@ -24,7 +24,7 @@
 #include <asm/tlbflush.h>
 #include <asm/cacheflush.h>
 
-static pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pmd_t *pmd;
@@ -39,7 +39,7 @@
 	return pte;
 }
 
-static pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pmd_t *pmd;
@@ -80,6 +80,20 @@
 	}
 }
 
+pte_t huge_ptep_get_and_clear(pte_t *ptep)
+{
+	pte_t entry;
+
+	entry = *ptep;
+
+	for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
+		pte_clear(pte);
+		pte++;
+	}
+
+	return entry;
+}
+
 /*
  * This function checks for proper alignment of input addr and len parameters.
  */
diff --git a/arch/sparc/mm/init.c b/arch/sparc/mm/init.c
index a2dea69..ec2e050 100644
--- a/arch/sparc/mm/init.c
+++ b/arch/sparc/mm/init.c
@@ -384,7 +384,6 @@
 		struct page *page = pfn_to_page(tmp);
 
 		ClearPageReserved(page);
-		set_bit(PG_highmem, &page->flags);
 		set_page_count(page, 1);
 		__free_page(page);
 		totalhigh_pages++;
diff --git a/arch/sparc64/kernel/sys_sparc.c b/arch/sparc64/kernel/sys_sparc.c
index 0077f02..5f8c822 100644
--- a/arch/sparc64/kernel/sys_sparc.c
+++ b/arch/sparc64/kernel/sys_sparc.c
@@ -84,6 +84,10 @@
 			return addr;
 	}
 
+	if (len <= mm->cached_hole_size) {
+	        mm->cached_hole_size = 0;
+		mm->free_area_cache = TASK_UNMAPPED_BASE;
+	}
 	start_addr = addr = mm->free_area_cache;
 
 	task_size -= len;
@@ -103,6 +107,7 @@
 		if (task_size < addr) {
 			if (start_addr != TASK_UNMAPPED_BASE) {
 				start_addr = addr = TASK_UNMAPPED_BASE;
+				mm->cached_hole_size = 0;
 				goto full_search;
 			}
 			return -ENOMEM;
@@ -114,6 +119,9 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
+
 		addr = vma->vm_end;
 		if (do_color_align)
 			addr = COLOUR_ALIGN(addr, pgoff);
diff --git a/arch/sparc64/lib/delay.c b/arch/sparc64/lib/delay.c
index f6b4c78..e880872 100644
--- a/arch/sparc64/lib/delay.c
+++ b/arch/sparc64/lib/delay.c
@@ -31,7 +31,7 @@
 {
 	n *= 4;
 
-	n *= (cpu_data(_smp_processor_id()).udelay_val * (HZ/4));
+	n *= (cpu_data(raw_smp_processor_id()).udelay_val * (HZ/4));
 	n >>= 32;
 
 	__delay(n + 1);
diff --git a/arch/sparc64/mm/hugetlbpage.c b/arch/sparc64/mm/hugetlbpage.c
index 5a1f831..625cbb3 100644
--- a/arch/sparc64/mm/hugetlbpage.c
+++ b/arch/sparc64/mm/hugetlbpage.c
@@ -22,7 +22,7 @@
 #include <asm/cacheflush.h>
 #include <asm/mmu_context.h>
 
-static pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pud_t *pud;
@@ -41,7 +41,7 @@
 	return pte;
 }
 
-static pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
+pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr)
 {
 	pgd_t *pgd;
 	pud_t *pud;
@@ -62,32 +62,36 @@
 
 #define mk_pte_huge(entry) do { pte_val(entry) |= _PAGE_SZHUGE; } while (0)
 
-static void set_huge_pte(struct mm_struct *mm, struct vm_area_struct *vma,
-			 unsigned long addr,
-			 struct page *page, pte_t * page_table, int write_access)
+void set_huge_pte_at(struct mm_struct *mm, unsigned long addr,
+		     pte_t *ptep, pte_t entry)
 {
-	unsigned long i;
-	pte_t entry;
-
-	add_mm_counter(mm, rss, HPAGE_SIZE / PAGE_SIZE);
-
-	if (write_access)
-		entry = pte_mkwrite(pte_mkdirty(mk_pte(page,
-						       vma->vm_page_prot)));
-	else
-		entry = pte_wrprotect(mk_pte(page, vma->vm_page_prot));
-	entry = pte_mkyoung(entry);
-	mk_pte_huge(entry);
+	int i;
 
 	for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
-		set_pte_at(mm, addr, page_table, entry);
-		page_table++;
+		set_pte_at(mm, addr, ptep, entry);
+		ptep++;
 		addr += PAGE_SIZE;
-
 		pte_val(entry) += PAGE_SIZE;
 	}
 }
 
+pte_t huge_ptep_get_and_clear(struct mm_struct *mm, unsigned long addr,
+			      pte_t *ptep)
+{
+	pte_t entry;
+	int i;
+
+	entry = *ptep;
+
+	for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
+		pte_clear(mm, addr, ptep);
+		addr += PAGE_SIZE;
+		ptep++;
+	}
+
+	return entry;
+}
+
 /*
  * This function checks for proper alignment of input addr and len parameters.
  */
@@ -100,79 +104,6 @@
 	return 0;
 }
 
-int copy_hugetlb_page_range(struct mm_struct *dst, struct mm_struct *src,
-			    struct vm_area_struct *vma)
-{
-	pte_t *src_pte, *dst_pte, entry;
-	struct page *ptepage;
-	unsigned long addr = vma->vm_start;
-	unsigned long end = vma->vm_end;
-	int i;
-
-	while (addr < end) {
-		dst_pte = huge_pte_alloc(dst, addr);
-		if (!dst_pte)
-			goto nomem;
-		src_pte = huge_pte_offset(src, addr);
-		BUG_ON(!src_pte || pte_none(*src_pte));
-		entry = *src_pte;
-		ptepage = pte_page(entry);
-		get_page(ptepage);
-		for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
-			set_pte_at(dst, addr, dst_pte, entry);
-			pte_val(entry) += PAGE_SIZE;
-			dst_pte++;
-			addr += PAGE_SIZE;
-		}
-		add_mm_counter(dst, rss, HPAGE_SIZE / PAGE_SIZE);
-	}
-	return 0;
-
-nomem:
-	return -ENOMEM;
-}
-
-int follow_hugetlb_page(struct mm_struct *mm, struct vm_area_struct *vma,
-			struct page **pages, struct vm_area_struct **vmas,
-			unsigned long *position, int *length, int i)
-{
-	unsigned long vaddr = *position;
-	int remainder = *length;
-
-	WARN_ON(!is_vm_hugetlb_page(vma));
-
-	while (vaddr < vma->vm_end && remainder) {
-		if (pages) {
-			pte_t *pte;
-			struct page *page;
-
-			pte = huge_pte_offset(mm, vaddr);
-
-			/* hugetlb should be locked, and hence, prefaulted */
-			BUG_ON(!pte || pte_none(*pte));
-
-			page = pte_page(*pte);
-
-			WARN_ON(!PageCompound(page));
-
-			get_page(page);
-			pages[i] = page;
-		}
-
-		if (vmas)
-			vmas[i] = vma;
-
-		vaddr += PAGE_SIZE;
-		--remainder;
-		++i;
-	}
-
-	*length = remainder;
-	*position = vaddr;
-
-	return i;
-}
-
 struct page *follow_huge_addr(struct mm_struct *mm,
 			      unsigned long address, int write)
 {
@@ -190,34 +121,6 @@
 	return NULL;
 }
 
-void unmap_hugepage_range(struct vm_area_struct *vma,
-			  unsigned long start, unsigned long end)
-{
-	struct mm_struct *mm = vma->vm_mm;
-	unsigned long address;
-	pte_t *pte;
-	struct page *page;
-	int i;
-
-	BUG_ON(start & (HPAGE_SIZE - 1));
-	BUG_ON(end & (HPAGE_SIZE - 1));
-
-	for (address = start; address < end; address += HPAGE_SIZE) {
-		pte = huge_pte_offset(mm, address);
-		BUG_ON(!pte);
-		if (pte_none(*pte))
-			continue;
-		page = pte_page(*pte);
-		put_page(page);
-		for (i = 0; i < (1 << HUGETLB_PAGE_ORDER); i++) {
-			pte_clear(mm, address+(i*PAGE_SIZE), pte);
-			pte++;
-		}
-	}
-	add_mm_counter(mm, rss, -((end - start) >> PAGE_SHIFT));
-	flush_tlb_range(vma, start, end);
-}
-
 static void context_reload(void *__data)
 {
 	struct mm_struct *mm = __data;
@@ -226,12 +129,8 @@
 		load_secondary_context(mm);
 }
 
-int hugetlb_prefault(struct address_space *mapping, struct vm_area_struct *vma)
+void hugetlb_prefault_arch_hook(struct mm_struct *mm)
 {
-	struct mm_struct *mm = current->mm;
-	unsigned long addr;
-	int ret = 0;
-
 	/* On UltraSPARC-III+ and later, configure the second half of
 	 * the Data-TLB for huge pages.
 	 */
@@ -261,50 +160,4 @@
 		}
 		spin_unlock(&ctx_alloc_lock);
 	}
-
-	BUG_ON(vma->vm_start & ~HPAGE_MASK);
-	BUG_ON(vma->vm_end & ~HPAGE_MASK);
-
-	spin_lock(&mm->page_table_lock);
-	for (addr = vma->vm_start; addr < vma->vm_end; addr += HPAGE_SIZE) {
-		unsigned long idx;
-		pte_t *pte = huge_pte_alloc(mm, addr);
-		struct page *page;
-
-		if (!pte) {
-			ret = -ENOMEM;
-			goto out;
-		}
-		if (!pte_none(*pte))
-			continue;
-
-		idx = ((addr - vma->vm_start) >> HPAGE_SHIFT)
-			+ (vma->vm_pgoff >> (HPAGE_SHIFT - PAGE_SHIFT));
-		page = find_get_page(mapping, idx);
-		if (!page) {
-			/* charge the fs quota first */
-			if (hugetlb_get_quota(mapping)) {
-				ret = -ENOMEM;
-				goto out;
-			}
-			page = alloc_huge_page();
-			if (!page) {
-				hugetlb_put_quota(mapping);
-				ret = -ENOMEM;
-				goto out;
-			}
-			ret = add_to_page_cache(page, mapping, idx, GFP_ATOMIC);
-			if (! ret) {
-				unlock_page(page);
-			} else {
-				hugetlb_put_quota(mapping);
-				free_huge_page(page);
-				goto out;
-			}
-		}
-		set_huge_pte(mm, vma, addr, page, pte, vma->vm_flags & VM_WRITE);
-	}
-out:
-	spin_unlock(&mm->page_table_lock);
-	return ret;
 }
diff --git a/arch/sparc64/solaris/socket.c b/arch/sparc64/solaris/socket.c
index ec8e074..0674058 100644
--- a/arch/sparc64/solaris/socket.c
+++ b/arch/sparc64/solaris/socket.c
@@ -317,8 +317,10 @@
 		unsigned long *kcmsg;
 		compat_size_t cmlen;
 
-		if(kern_msg.msg_controllen > sizeof(ctl) &&
-		   kern_msg.msg_controllen <= 256) {
+		if (kern_msg.msg_controllen <= sizeof(compat_size_t))
+			return -EINVAL;
+
+		if(kern_msg.msg_controllen > sizeof(ctl)) {
 			err = -ENOBUFS;
 			ctl_buf = kmalloc(kern_msg.msg_controllen, GFP_KERNEL);
 			if(!ctl_buf)
diff --git a/arch/um/Kconfig b/arch/um/Kconfig
index c529218..b8e952c 100644
--- a/arch/um/Kconfig
+++ b/arch/um/Kconfig
@@ -35,6 +35,11 @@
 	bool
 	default y
 
+# Used in kernel/irq/manage.c and include/linux/irq.h
+config IRQ_RELEASE_METHOD
+	bool
+	default y
+
 menu "UML-specific options"
 
 config MODE_TT
diff --git a/arch/um/Makefile b/arch/um/Makefile
index f2a0c40..3f07390 100644
--- a/arch/um/Makefile
+++ b/arch/um/Makefile
@@ -122,7 +122,7 @@
 CPPFLAGS_vmlinux.lds = $(shell echo -U$(SUBARCH) \
 	-DSTART=$(START) -DELF_ARCH=$(ELF_ARCH) \
 	-DELF_FORMAT=\"$(ELF_FORMAT)\" $(CPP_MODE-y) \
-	-DKERNEL_STACK_SIZE=$(STACK_SIZE))
+	-DKERNEL_STACK_SIZE=$(STACK_SIZE) -DSUBARCH=$(SUBARCH))
 
 #The wrappers will select whether using "malloc" or the kernel allocator.
 LINK_WRAPS = -Wl,--wrap,malloc -Wl,--wrap,free -Wl,--wrap,calloc
diff --git a/arch/um/drivers/line.c b/arch/um/drivers/line.c
index 025d3be..0f59736 100644
--- a/arch/um/drivers/line.c
+++ b/arch/um/drivers/line.c
@@ -406,14 +406,12 @@
 	if(line->driver->read_irq == current_irq)
 		free_irq_later(line->driver->read_irq, tty);
 	else {
-		free_irq_by_irq_and_dev(line->driver->read_irq, tty);
 		free_irq(line->driver->read_irq, tty);
 	}
 
 	if(line->driver->write_irq == current_irq)
 		free_irq_later(line->driver->write_irq, tty);
 	else {
-		free_irq_by_irq_and_dev(line->driver->write_irq, tty);
 		free_irq(line->driver->write_irq, tty);
 	}
 
@@ -758,7 +756,6 @@
         if(winch->pid != -1)
                 os_kill_process(winch->pid, 1);
 
-        free_irq_by_irq_and_dev(WINCH_IRQ, winch);
         free_irq(WINCH_IRQ, winch);
         list_del(&winch->list);
         kfree(winch);
diff --git a/arch/um/drivers/net_kern.c b/arch/um/drivers/net_kern.c
index 4eeaf88..5388a74 100644
--- a/arch/um/drivers/net_kern.c
+++ b/arch/um/drivers/net_kern.c
@@ -146,7 +146,6 @@
 	netif_stop_queue(dev);
 	spin_lock(&lp->lock);
 
-	free_irq_by_irq_and_dev(dev->irq, dev);
 	free_irq(dev->irq, dev);
 	if(lp->close != NULL)
 		(*lp->close)(lp->fd, &lp->user);
diff --git a/arch/um/drivers/port_kern.c b/arch/um/drivers/port_kern.c
index b5ee074..c41efd2 100644
--- a/arch/um/drivers/port_kern.c
+++ b/arch/um/drivers/port_kern.c
@@ -257,7 +257,6 @@
 		 * connection.  Then we loop here throwing out failed 
 		 * connections until a good one is found.
 		 */
-		free_irq_by_irq_and_dev(TELNETD_IRQ, conn);
 		free_irq(TELNETD_IRQ, conn);
 
 		if(conn->fd >= 0) break;
diff --git a/arch/um/drivers/xterm_kern.c b/arch/um/drivers/xterm_kern.c
index a4fdf35..d269a80 100644
--- a/arch/um/drivers/xterm_kern.c
+++ b/arch/um/drivers/xterm_kern.c
@@ -69,7 +69,6 @@
 	 * isn't set) this will hang... */
 	wait_for_completion(&data->ready);
 
-	free_irq_by_irq_and_dev(XTERM_IRQ, data);
 	free_irq(XTERM_IRQ, data);
 
 	ret = data->new_fd;
diff --git a/arch/um/kernel/irq.c b/arch/um/kernel/irq.c
index d44fb52..9f18061 100644
--- a/arch/um/kernel/irq.c
+++ b/arch/um/kernel/irq.c
@@ -124,14 +124,16 @@
 	spin_unlock_irqrestore(&irq_spinlock, flags);
 }
 
-/*  presently hw_interrupt_type must define (startup || enable) &&
- *  disable && end */
+/* hw_interrupt_type must define (startup || enable) &&
+ * (shutdown || disable) && end */
 static void dummy(unsigned int irq)
 {
 }
 
-static struct hw_interrupt_type SIGIO_irq_type = {
+/* This is used for everything else than the timer. */
+static struct hw_interrupt_type normal_irq_type = {
 	.typename = "SIGIO",
+	.release = free_irq_by_irq_and_dev,
 	.disable = dummy,
 	.enable = dummy,
 	.ack = dummy,
@@ -140,6 +142,7 @@
 
 static struct hw_interrupt_type SIGVTALRM_irq_type = {
 	.typename = "SIGVTALRM",
+	.release = free_irq_by_irq_and_dev,
 	.shutdown = dummy, /* never called */
 	.disable = dummy,
 	.enable = dummy,
@@ -160,7 +163,7 @@
 		irq_desc[i].status = IRQ_DISABLED;
 		irq_desc[i].action = NULL;
 		irq_desc[i].depth = 1;
-		irq_desc[i].handler = &SIGIO_irq_type;
+		irq_desc[i].handler = &normal_irq_type;
 		enable_irq(i);
 	}
 }
diff --git a/arch/um/kernel/irq_user.c b/arch/um/kernel/irq_user.c
index b3074cb..c3ccaf24 100644
--- a/arch/um/kernel/irq_user.c
+++ b/arch/um/kernel/irq_user.c
@@ -85,8 +85,6 @@
 				next = irq_fd->next;
 				if(irq_fd->freed){
 					free_irq(irq_fd->irq, irq_fd->id);
-					free_irq_by_irq_and_dev(irq_fd->irq,
-								irq_fd->id);
 				}
 			}
 		}
diff --git a/arch/um/kernel/mem.c b/arch/um/kernel/mem.c
index c22825f..5597bd3 100644
--- a/arch/um/kernel/mem.c
+++ b/arch/um/kernel/mem.c
@@ -53,7 +53,6 @@
 	for(i = 0; i < highmem_len >> PAGE_SHIFT; i++){
 		page = &mem_map[highmem_pfn + i];
 		ClearPageReserved(page);
-		set_bit(PG_highmem, &page->flags);
 		set_page_count(page, 1);
 		__free_page(page);
 	}
diff --git a/arch/um/kernel/tt/Makefile b/arch/um/kernel/tt/Makefile
index c3faea2..3fd2554 100644
--- a/arch/um/kernel/tt/Makefile
+++ b/arch/um/kernel/tt/Makefile
@@ -3,10 +3,6 @@
 # Licensed under the GPL
 #
 
-extra-y := unmap_fin.o
-targets := unmap.o
-clean-files := unmap_tmp.o
-
 obj-y = exec_kern.o exec_user.o gdb.o ksyms.o mem.o mem_user.o process_kern.o \
 	syscall_kern.o syscall_user.o time.o tlb.o tracer.o trap_user.o \
 	uaccess.o uaccess_user.o
@@ -16,14 +12,3 @@
 USER_OBJS := gdb.o time.o tracer.o
 
 include arch/um/scripts/Makefile.rules
-
-UNMAP_CFLAGS := $(patsubst -pg -DPROFILING,,$(USER_CFLAGS))
-UNMAP_CFLAGS := $(patsubst -fprofile-arcs -ftest-coverage,,$(UNMAP_CFLAGS))
-
-#XXX: partially copied from arch/um/scripts/Makefile.rules
-$(obj)/unmap.o: c_flags = -Wp,-MD,$(depfile) $(UNMAP_CFLAGS)
-
-$(obj)/unmap_fin.o : $(obj)/unmap.o
-	$(LD) -r -o $(obj)/unmap_tmp.o $< $(shell $(CC) -print-file-name=libc.a)
-	$(OBJCOPY) $(obj)/unmap_tmp.o $@ -G switcheroo
-
diff --git a/arch/um/kernel/tt/unmap.c b/arch/um/kernel/tt/unmap.c
deleted file mode 100644
index 3f7aecd..0000000
--- a/arch/um/kernel/tt/unmap.c
+++ /dev/null
@@ -1,31 +0,0 @@
-/* 
- * Copyright (C) 2000 Jeff Dike (jdike@karaya.com)
- * Licensed under the GPL
- */
-
-#include <sys/mman.h>
-
-int switcheroo(int fd, int prot, void *from, void *to, int size)
-{
-	if(munmap(to, size) < 0){
-		return(-1);
-	}
-	if(mmap(to, size, prot,	MAP_SHARED | MAP_FIXED, fd, 0) != to){
-		return(-1);
-	}
-	if(munmap(from, size) < 0){
-		return(-1);
-	}
-	return(0);
-}
-
-/*
- * Overrides for Emacs so that we follow Linus's tabbing style.
- * Emacs will notice this stuff at the end of the file and automatically
- * adjust the settings for this buffer only.  This must remain at the end
- * of the file.
- * ---------------------------------------------------------------------------
- * Local variables:
- * c-file-style: "linux"
- * End:
- */
diff --git a/arch/um/kernel/uml.lds.S b/arch/um/kernel/uml.lds.S
index dd53555..61dfd4f 100644
--- a/arch/um/kernel/uml.lds.S
+++ b/arch/um/kernel/uml.lds.S
@@ -14,19 +14,10 @@
   /* Used in arch/um/kernel/mem.c. Any memory between START and __binary_start
    * is remapped.*/
   __binary_start = .;
-#ifdef MODE_TT
-  .thread_private : {
-    __start_thread_private = .;
-    errno = .;
-    . += 4;
-    arch/um/kernel/tt/unmap_fin.o (.data)
-    __end_thread_private = .;
-  }
-  . = ALIGN(4096);
-  .remap : { arch/um/kernel/tt/unmap_fin.o (.text) }
 
-  /* We want it only if we are in MODE_TT. In both cases, however, when MODE_TT
-   * is off the resulting binary segfaults.*/
+#ifdef MODE_TT
+  .remap_data : { arch/um/sys-SUBARCH/unmap_fin.o (.data .bss) }
+  .remap : { arch/um/sys-SUBARCH/unmap_fin.o (.text) }
 
   . = ALIGN(4096);		/* Init code and data */
 #endif
diff --git a/arch/um/scripts/Makefile.rules b/arch/um/scripts/Makefile.rules
index 98346c7..7459d09 100644
--- a/arch/um/scripts/Makefile.rules
+++ b/arch/um/scripts/Makefile.rules
@@ -10,6 +10,12 @@
 $(USER_OBJS) : c_flags = -Wp,-MD,$(depfile) $(USER_CFLAGS) \
 	$(CFLAGS_$(notdir $@))
 
+# The stubs and unmap.o can't try to call mcount or update basic block data
+define unprofile
+	$(patsubst -pg,,$(patsubst -fprofile-arcs -ftest-coverage,,$(1)))
+endef
+
+
 quiet_cmd_make_link = SYMLINK $@
 cmd_make_link       = ln -sf $(srctree)/arch/$(SUBARCH)/$($(notdir $@)-dir)/$(notdir $@) $@
 
diff --git a/arch/um/scripts/Makefile.unmap b/arch/um/scripts/Makefile.unmap
new file mode 100644
index 0000000..37a8f97
--- /dev/null
+++ b/arch/um/scripts/Makefile.unmap
@@ -0,0 +1,22 @@
+clean-files += unmap_tmp.o unmap_fin.o unmap.o
+
+ifdef CONFIG_MODE_TT
+
+#Always build unmap_fin.o
+extra-y += unmap_fin.o
+#Do dependency tracking for unmap.o (it will be always built, but won't get the tracking unless we use this).
+targets += unmap.o
+
+#XXX: partially copied from arch/um/scripts/Makefile.rules
+$(obj)/unmap.o: _c_flags = $(call unprofile,$(CFLAGS))
+
+quiet_cmd_wrapld = LD      $@
+define cmd_wrapld
+	$(LD) -r -o $(obj)/unmap_tmp.o $< $(shell $(CC) -print-file-name=libc.a); \
+	$(OBJCOPY) $(obj)/unmap_tmp.o $@ -G switcheroo
+endef
+
+$(obj)/unmap_fin.o : $(obj)/unmap.o FORCE
+	$(call if_changed,wrapld)
+
+endif
diff --git a/arch/um/sys-i386/Makefile b/arch/um/sys-i386/Makefile
index 4351e56..095bcdb 100644
--- a/arch/um/sys-i386/Makefile
+++ b/arch/um/sys-i386/Makefile
@@ -17,3 +17,5 @@
 module.c-dir = kernel
 
 subdir- := util
+
+include arch/um/scripts/Makefile.unmap
diff --git a/arch/um/sys-i386/unmap.c b/arch/um/sys-i386/unmap.c
new file mode 100644
index 0000000..1368752
--- /dev/null
+++ b/arch/um/sys-i386/unmap.c
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2000 Jeff Dike (jdike@karaya.com)
+ * Licensed under the GPL
+ */
+
+#include <linux/mman.h>
+#include <asm/unistd.h>
+
+static int errno;
+
+static inline _syscall2(int,munmap,void *,start,size_t,len)
+static inline _syscall6(void *,mmap2,void *,addr,size_t,len,int,prot,int,flags,int,fd,off_t,offset)
+int switcheroo(int fd, int prot, void *from, void *to, int size)
+{
+	if(munmap(to, size) < 0){
+		return(-1);
+	}
+	if(mmap2(to, size, prot, MAP_SHARED | MAP_FIXED, fd, 0) != to){
+		return(-1);
+	}
+	if(munmap(from, size) < 0){
+		return(-1);
+	}
+	return(0);
+}
diff --git a/arch/um/sys-x86_64/Makefile b/arch/um/sys-x86_64/Makefile
index 608466a..2bc6f68 100644
--- a/arch/um/sys-x86_64/Makefile
+++ b/arch/um/sys-x86_64/Makefile
@@ -29,3 +29,5 @@
 module.c-dir = kernel
 
 subdir- := util
+
+include arch/um/scripts/Makefile.unmap
diff --git a/arch/um/sys-x86_64/unmap.c b/arch/um/sys-x86_64/unmap.c
new file mode 100644
index 0000000..bc7094c
--- /dev/null
+++ b/arch/um/sys-x86_64/unmap.c
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2000 Jeff Dike (jdike@karaya.com)
+ * Licensed under the GPL
+ */
+
+#include <linux/mman.h>
+#include <asm/unistd.h>
+
+static int errno;
+
+static inline _syscall2(int,munmap,void *,start,size_t,len)
+static inline _syscall6(void *,mmap,void *,addr,size_t,len,int,prot,int,flags,int,fd,off_t,offset)
+int switcheroo(int fd, int prot, void *from, void *to, int size)
+{
+	if(munmap(to, size) < 0){
+		return(-1);
+	}
+	if(mmap(to, size, prot, MAP_SHARED | MAP_FIXED, fd, 0) != to){
+		return(-1);
+	}
+	if(munmap(from, size) < 0){
+		return(-1);
+	}
+	return(0);
+}
diff --git a/arch/x86_64/ia32/ia32_aout.c b/arch/x86_64/ia32/ia32_aout.c
index 1965efc..c12edf5 100644
--- a/arch/x86_64/ia32/ia32_aout.c
+++ b/arch/x86_64/ia32/ia32_aout.c
@@ -312,6 +312,7 @@
 	current->mm->brk = ex.a_bss +
 		(current->mm->start_brk = N_BSSADDR(ex));
 	current->mm->free_area_cache = TASK_UNMAPPED_BASE;
+	current->mm->cached_hole_size = 0;
 
 	set_mm_counter(current->mm, rss, 0);
 	current->mm->mmap = NULL;
diff --git a/arch/x86_64/ia32/ia32_binfmt.c b/arch/x86_64/ia32/ia32_binfmt.c
index 99b5220..c8131f3 100644
--- a/arch/x86_64/ia32/ia32_binfmt.c
+++ b/arch/x86_64/ia32/ia32_binfmt.c
@@ -46,7 +46,7 @@
 
 #define IA32_EMULATOR 1
 
-#define ELF_ET_DYN_BASE		(TASK_UNMAPPED_32 + 0x1000000)
+#define ELF_ET_DYN_BASE		(TASK_UNMAPPED_BASE + 0x1000000)
 
 #undef ELF_ARCH
 #define ELF_ARCH EM_386
@@ -307,9 +307,6 @@
 
 #define elf_addr_t __u32
 
-#undef TASK_SIZE
-#define TASK_SIZE 0xffffffff
-
 static void elf32_init(struct pt_regs *);
 
 #define ARCH_HAS_SETUP_ADDITIONAL_PAGES 1
diff --git a/arch/x86_64/kernel/process.c b/arch/x86_64/kernel/process.c
index 761b6d3..dce8bab 100644
--- a/arch/x86_64/kernel/process.c
+++ b/arch/x86_64/kernel/process.c
@@ -656,7 +656,7 @@
 
 	switch (code) { 
 	case ARCH_SET_GS:
-		if (addr >= TASK_SIZE) 
+		if (addr >= TASK_SIZE_OF(task))
 			return -EPERM; 
 		cpu = get_cpu();
 		/* handle small bases via the GDT because that's faster to 
@@ -682,7 +682,7 @@
 	case ARCH_SET_FS:
 		/* Not strictly needed for fs, but do it for symmetry
 		   with gs */
-		if (addr >= TASK_SIZE)
+		if (addr >= TASK_SIZE_OF(task))
 			return -EPERM; 
 		cpu = get_cpu();
 		/* handle small bases via the GDT because that's faster to 
diff --git a/arch/x86_64/kernel/ptrace.c b/arch/x86_64/kernel/ptrace.c
index 525f6a1..bbf64b5 100644
--- a/arch/x86_64/kernel/ptrace.c
+++ b/arch/x86_64/kernel/ptrace.c
@@ -257,12 +257,12 @@
 			value &= 0xffff;
 			return 0;
 		case offsetof(struct user_regs_struct,fs_base):
-			if (value >= TASK_SIZE)
+			if (value >= TASK_SIZE_OF(child))
 				return -EIO;
 			child->thread.fs = value;
 			return 0;
 		case offsetof(struct user_regs_struct,gs_base):
-			if (value >= TASK_SIZE)
+			if (value >= TASK_SIZE_OF(child))
 				return -EIO;
 			child->thread.gs = value;
 			return 0;
@@ -279,7 +279,7 @@
 			break;
 		case offsetof(struct user_regs_struct, rip):
 			/* Check if the new RIP address is canonical */
-			if (value >= TASK_SIZE)
+			if (value >= TASK_SIZE_OF(child))
 				return -EIO;
 			break;
 	}
@@ -419,6 +419,8 @@
 		break;
 
 	case PTRACE_POKEUSR: /* write the word at location addr in the USER area */
+	{
+		int dsize = test_tsk_thread_flag(child, TIF_IA32) ? 3 : 7;
 		ret = -EIO;
 		if ((addr & 7) ||
 		    addr > sizeof(struct user) - 7)
@@ -430,22 +432,22 @@
 			break;
 		/* Disallows to set a breakpoint into the vsyscall */
 		case offsetof(struct user, u_debugreg[0]):
-			if (data >= TASK_SIZE-7) break;
+			if (data >= TASK_SIZE_OF(child) - dsize) break;
 			child->thread.debugreg0 = data;
 			ret = 0;
 			break;
 		case offsetof(struct user, u_debugreg[1]):
-			if (data >= TASK_SIZE-7) break;
+			if (data >= TASK_SIZE_OF(child) - dsize) break;
 			child->thread.debugreg1 = data;
 			ret = 0;
 			break;
 		case offsetof(struct user, u_debugreg[2]):
-			if (data >= TASK_SIZE-7) break;
+			if (data >= TASK_SIZE_OF(child) - dsize) break;
 			child->thread.debugreg2 = data;
 			ret = 0;
 			break;
 		case offsetof(struct user, u_debugreg[3]):
-			if (data >= TASK_SIZE-7) break;
+			if (data >= TASK_SIZE_OF(child) - dsize) break;
 			child->thread.debugreg3 = data;
 			ret = 0;
 			break;
@@ -469,6 +471,7 @@
 		  break;
 		}
 		break;
+	}
 	case PTRACE_SYSCALL: /* continue and stop at next (return from) syscall */
 	case PTRACE_CONT:    /* restart after signal. */
 
diff --git a/arch/x86_64/kernel/sys_x86_64.c b/arch/x86_64/kernel/sys_x86_64.c
index dbebd5c..cc7821c 100644
--- a/arch/x86_64/kernel/sys_x86_64.c
+++ b/arch/x86_64/kernel/sys_x86_64.c
@@ -68,13 +68,7 @@
 static void find_start_end(unsigned long flags, unsigned long *begin,
 			   unsigned long *end)
 {
-#ifdef CONFIG_IA32_EMULATION
-	if (test_thread_flag(TIF_IA32)) { 
-		*begin = TASK_UNMAPPED_32;
-		*end = IA32_PAGE_OFFSET; 
-	} else 
-#endif
-	if (flags & MAP_32BIT) { 
+	if (!test_thread_flag(TIF_IA32) && (flags & MAP_32BIT)) {
 		/* This is usually used needed to map code in small
 		   model, so it needs to be in the first 31bit. Limit
 		   it to that.  This means we need to move the
@@ -84,10 +78,10 @@
 		   of playground for now. -AK */ 
 		*begin = 0x40000000; 
 		*end = 0x80000000;		
-	} else { 
-		*begin = TASK_UNMAPPED_64; 
+	} else {
+		*begin = TASK_UNMAPPED_BASE;
 		*end = TASK_SIZE; 
-		}
+	}
 } 
 
 unsigned long
@@ -111,6 +105,11 @@
 		    (!vma || addr + len <= vma->vm_start))
 			return addr;
 	}
+	if (((flags & MAP_32BIT) || test_thread_flag(TIF_IA32))
+	    && len <= mm->cached_hole_size) {
+	        mm->cached_hole_size = 0;
+		mm->free_area_cache = begin;
+	}
 	addr = mm->free_area_cache;
 	if (addr < begin) 
 		addr = begin; 
@@ -126,6 +125,7 @@
 			 */
 			if (start_addr != begin) {
 				start_addr = addr = begin;
+				mm->cached_hole_size = 0;
 				goto full_search;
 			}
 			return -ENOMEM;
@@ -137,6 +137,9 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
+
 		addr = vma->vm_end;
 	}
 }
diff --git a/arch/x86_64/lib/delay.c b/arch/x86_64/lib/delay.c
index 6e2d664..aed61a6 100644
--- a/arch/x86_64/lib/delay.c
+++ b/arch/x86_64/lib/delay.c
@@ -34,7 +34,7 @@
 
 inline void __const_udelay(unsigned long xloops)
 {
-	__delay(((xloops * cpu_data[_smp_processor_id()].loops_per_jiffy) >> 32) * HZ);
+	__delay(((xloops * cpu_data[raw_smp_processor_id()].loops_per_jiffy) >> 32) * HZ);
 }
 
 void __udelay(unsigned long usecs)
diff --git a/arch/x86_64/mm/fault.c b/arch/x86_64/mm/fault.c
index 5d6b211..57d3ab1 100644
--- a/arch/x86_64/mm/fault.c
+++ b/arch/x86_64/mm/fault.c
@@ -350,7 +350,7 @@
 	 * (error_code & 4) == 0, and that the fault was not a
 	 * protection error (error_code & 1) == 0.
 	 */
-	if (unlikely(address >= TASK_SIZE)) {
+	if (unlikely(address >= TASK_SIZE64)) {
 		if (!(error_code & 5) &&
 		      ((address >= VMALLOC_START && address < VMALLOC_END) ||
 		       (address >= MODULES_VADDR && address < MODULES_END))) {
diff --git a/drivers/Kconfig b/drivers/Kconfig
index ed41d90..aed4a9b 100644
--- a/drivers/Kconfig
+++ b/drivers/Kconfig
@@ -58,4 +58,6 @@
 
 source "drivers/infiniband/Kconfig"
 
+source "drivers/sn/Kconfig"
+
 endmenu
diff --git a/drivers/Makefile b/drivers/Makefile
index 15681de..3167be5 100644
--- a/drivers/Makefile
+++ b/drivers/Makefile
@@ -61,6 +61,6 @@
 obj-$(CONFIG_CPU_FREQ)		+= cpufreq/
 obj-$(CONFIG_MMC)		+= mmc/
 obj-$(CONFIG_INFINIBAND)	+= infiniband/
-obj-$(CONFIG_BLK_DEV_SGIIOC4)	+= sn/
+obj-$(CONFIG_SGI_IOC4)		+= sn/
 obj-y				+= firmware/
 obj-$(CONFIG_CRYPTO)		+= crypto/
diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
index ff64d33..c9d671c 100644
--- a/drivers/acpi/processor_idle.c
+++ b/drivers/acpi/processor_idle.c
@@ -171,7 +171,7 @@
 	int			sleep_ticks = 0;
 	u32			t1, t2 = 0;
 
-	pr = processors[_smp_processor_id()];
+	pr = processors[raw_smp_processor_id()];
 	if (!pr)
 		return;
 
diff --git a/drivers/base/node.c b/drivers/base/node.c
index 5d4517c..904b27c 100644
--- a/drivers/base/node.c
+++ b/drivers/base/node.c
@@ -87,7 +87,7 @@
 	for (i = 0; i < MAX_NR_ZONES; i++) {
 		struct zone *z = &pg->node_zones[i];
 		for (cpu = 0; cpu < NR_CPUS; cpu++) {
-			struct per_cpu_pageset *ps = &z->pageset[cpu];
+			struct per_cpu_pageset *ps = zone_pcp(z,cpu);
 			numa_hit += ps->numa_hit;
 			numa_miss += ps->numa_miss;
 			numa_foreign += ps->numa_foreign;
diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig
index 5ed6515..7ccf871 100644
--- a/drivers/char/Kconfig
+++ b/drivers/char/Kconfig
@@ -929,6 +929,10 @@
 
 	  If compiled as a module, it will be called scx200_gpio.
 
+config GPIO_VR41XX
+	tristate "NEC VR4100 series General-purpose I/O Unit support"
+	depends on CPU_VR41XX
+
 config RAW_DRIVER
 	tristate "RAW driver (/dev/raw/rawN) (OBSOLETE)"
 	help
diff --git a/drivers/char/Makefile b/drivers/char/Makefile
index e3f5c32..1aff819 100644
--- a/drivers/char/Makefile
+++ b/drivers/char/Makefile
@@ -80,6 +80,7 @@
 obj-$(CONFIG_NWBUTTON) += nwbutton.o
 obj-$(CONFIG_NWFLASH) += nwflash.o
 obj-$(CONFIG_SCx200_GPIO) += scx200_gpio.o
+obj-$(CONFIG_GPIO_VR41XX) += vr41xx_giu.o
 obj-$(CONFIG_TANBAC_TB0219) += tb0219.o
 
 obj-$(CONFIG_WATCHDOG)	+= watchdog/
diff --git a/drivers/char/ipmi/ipmi_msghandler.c b/drivers/char/ipmi/ipmi_msghandler.c
index d7fb452..0c81652 100644
--- a/drivers/char/ipmi/ipmi_msghandler.c
+++ b/drivers/char/ipmi/ipmi_msghandler.c
@@ -641,7 +641,7 @@
 		return -ENOMEM;
 
 	down_read(&interfaces_sem);
-	if ((if_num > MAX_IPMI_INTERFACES) || ipmi_interfaces[if_num] == NULL)
+	if ((if_num >= MAX_IPMI_INTERFACES) || ipmi_interfaces[if_num] == NULL)
 	{
 		rv = -EINVAL;
 		goto out_unlock;
diff --git a/drivers/char/mem.c b/drivers/char/mem.c
index 257b8ee..e3085b2 100644
--- a/drivers/char/mem.c
+++ b/drivers/char/mem.c
@@ -484,7 +484,7 @@
  	return virtr + wrote;
 }
 
-#if defined(CONFIG_ISA) || !defined(__mc68000__)
+#if (defined(CONFIG_ISA) || !defined(__mc68000__)) && (!defined(CONFIG_PPC_ISERIES) || defined(CONFIG_PCI))
 static ssize_t read_port(struct file * file, char __user * buf,
 			 size_t count, loff_t *ppos)
 {
@@ -744,7 +744,7 @@
 	.write		= write_null,
 };
 
-#if defined(CONFIG_ISA) || !defined(__mc68000__)
+#if (defined(CONFIG_ISA) || !defined(__mc68000__)) && (!defined(CONFIG_PPC_ISERIES) || defined(CONFIG_PCI))
 static struct file_operations port_fops = {
 	.llseek		= memory_lseek,
 	.read		= read_port,
@@ -804,7 +804,7 @@
 		case 3:
 			filp->f_op = &null_fops;
 			break;
-#if defined(CONFIG_ISA) || !defined(__mc68000__)
+#if (defined(CONFIG_ISA) || !defined(__mc68000__)) && (!defined(CONFIG_PPC_ISERIES) || defined(CONFIG_PCI))
 		case 4:
 			filp->f_op = &port_fops;
 			break;
@@ -846,7 +846,7 @@
 	{1, "mem",     S_IRUSR | S_IWUSR | S_IRGRP, &mem_fops},
 	{2, "kmem",    S_IRUSR | S_IWUSR | S_IRGRP, &kmem_fops},
 	{3, "null",    S_IRUGO | S_IWUGO,           &null_fops},
-#if defined(CONFIG_ISA) || !defined(__mc68000__)
+#if (defined(CONFIG_ISA) || !defined(__mc68000__)) && (!defined(CONFIG_PPC_ISERIES) || defined(CONFIG_PCI))
 	{4, "port",    S_IRUSR | S_IWUSR | S_IRGRP, &port_fops},
 #endif
 	{5, "zero",    S_IRUGO | S_IWUGO,           &zero_fops},
diff --git a/drivers/char/vr41xx_giu.c b/drivers/char/vr41xx_giu.c
new file mode 100644
index 0000000..683278b
--- /dev/null
+++ b/drivers/char/vr41xx_giu.c
@@ -0,0 +1,743 @@
+/*
+ *  Driver for NEC VR4100 series General-purpose I/O Unit.
+ *
+ *  Copyright (C) 2002 MontaVista Software Inc.
+ *	Author: Yoichi Yuasa <yyuasa@mvista.com or source@mvista.com>
+ *  Copyright (C) 2003-2005  Yoichi Yuasa <yuasa@hh.iij4u.or.jp>
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+#include <linux/device.h>
+#include <linux/errno.h>
+#include <linux/fs.h>
+#include <linux/init.h>
+#include <linux/irq.h>
+#include <linux/interrupt.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/spinlock.h>
+#include <linux/types.h>
+
+#include <asm/cpu.h>
+#include <asm/io.h>
+#include <asm/vr41xx/giu.h>
+#include <asm/vr41xx/vr41xx.h>
+
+MODULE_AUTHOR("Yoichi Yuasa <yuasa@hh.iij4u.or.jp>");
+MODULE_DESCRIPTION("NEC VR4100 series General-purpose I/O Unit driver");
+MODULE_LICENSE("GPL");
+
+static int major;	/* default is dynamic major device number */
+module_param(major, int, 0);
+MODULE_PARM_DESC(major, "Major device number");
+
+#define GIU_TYPE1_START		0x0b000100UL
+#define GIU_TYPE1_SIZE		0x20UL
+
+#define GIU_TYPE2_START		0x0f000140UL
+#define GIU_TYPE2_SIZE		0x20UL
+
+#define GIU_TYPE3_START		0x0f000140UL
+#define GIU_TYPE3_SIZE		0x28UL
+
+#define GIU_PULLUPDOWN_START	0x0b0002e0UL
+#define GIU_PULLUPDOWN_SIZE	0x04UL
+
+#define GIUIOSELL	0x00
+#define GIUIOSELH	0x02
+#define GIUPIODL	0x04
+#define GIUPIODH	0x06
+#define GIUINTSTATL	0x08
+#define GIUINTSTATH	0x0a
+#define GIUINTENL	0x0c
+#define GIUINTENH	0x0e
+#define GIUINTTYPL	0x10
+#define GIUINTTYPH	0x12
+#define GIUINTALSELL	0x14
+#define GIUINTALSELH	0x16
+#define GIUINTHTSELL	0x18
+#define GIUINTHTSELH	0x1a
+#define GIUPODATL	0x1c
+#define GIUPODATEN	0x1c
+#define GIUPODATH	0x1e
+ #define PIOEN0		0x0100
+ #define PIOEN1		0x0200
+#define GIUPODAT	0x1e
+#define GIUFEDGEINHL	0x20
+#define GIUFEDGEINHH	0x22
+#define GIUREDGEINHL	0x24
+#define GIUREDGEINHH	0x26
+
+#define GIUUSEUPDN	0x1e0
+#define GIUTERMUPDN	0x1e2
+
+#define GPIO_HAS_PULLUPDOWN_IO		0x0001
+#define GPIO_HAS_OUTPUT_ENABLE		0x0002
+#define GPIO_HAS_INTERRUPT_EDGE_SELECT	0x0100
+
+static spinlock_t giu_lock;
+static struct resource *giu_resource1;
+static struct resource *giu_resource2;
+static unsigned long giu_flags;
+static unsigned int giu_nr_pins;
+
+static void __iomem *giu_base;
+
+#define giu_read(offset)		readw(giu_base + (offset))
+#define giu_write(offset, value)	writew((value), giu_base + (offset))
+
+#define GPIO_PIN_OF_IRQ(irq)	((irq) - GIU_IRQ_BASE)
+#define GIUINT_HIGH_OFFSET	16
+#define GIUINT_HIGH_MAX		32
+
+static inline uint16_t giu_set(uint16_t offset, uint16_t set)
+{
+	uint16_t data;
+
+	data = giu_read(offset);
+	data |= set;
+	giu_write(offset, data);
+
+	return data;
+}
+
+static inline uint16_t giu_clear(uint16_t offset, uint16_t clear)
+{
+	uint16_t data;
+
+	data = giu_read(offset);
+	data &= ~clear;
+	giu_write(offset, data);
+
+	return data;
+}
+
+static unsigned int startup_giuint_low_irq(unsigned int irq)
+{
+	unsigned int pin;
+
+	pin = GPIO_PIN_OF_IRQ(irq);
+	giu_write(GIUINTSTATL, 1 << pin);
+	giu_set(GIUINTENL, 1 << pin);
+
+	return 0;
+}
+
+static void shutdown_giuint_low_irq(unsigned int irq)
+{
+	giu_clear(GIUINTENL, 1 << GPIO_PIN_OF_IRQ(irq));
+}
+
+static void enable_giuint_low_irq(unsigned int irq)
+{
+	giu_set(GIUINTENL, 1 << GPIO_PIN_OF_IRQ(irq));
+}
+
+#define disable_giuint_low_irq	shutdown_giuint_low_irq
+
+static void ack_giuint_low_irq(unsigned int irq)
+{
+	unsigned int pin;
+
+	pin = GPIO_PIN_OF_IRQ(irq);
+	giu_clear(GIUINTENL, 1 << pin);
+	giu_write(GIUINTSTATL, 1 << pin);
+}
+
+static void end_giuint_low_irq(unsigned int irq)
+{
+	if (!(irq_desc[irq].status & (IRQ_DISABLED | IRQ_INPROGRESS)))
+		giu_set(GIUINTENL, 1 << GPIO_PIN_OF_IRQ(irq));
+}
+
+static struct hw_interrupt_type giuint_low_irq_type = {
+	.typename	= "GIUINTL",
+	.startup	= startup_giuint_low_irq,
+	.shutdown	= shutdown_giuint_low_irq,
+	.enable		= enable_giuint_low_irq,
+	.disable	= disable_giuint_low_irq,
+	.ack		= ack_giuint_low_irq,
+	.end		= end_giuint_low_irq,
+};
+
+static unsigned int startup_giuint_high_irq(unsigned int irq)
+{
+	unsigned int pin;
+
+	pin = GPIO_PIN_OF_IRQ(irq) - GIUINT_HIGH_OFFSET;
+	giu_write(GIUINTSTATH, 1 << pin);
+	giu_set(GIUINTENH, 1 << pin);
+
+	return 0;
+}
+
+static void shutdown_giuint_high_irq(unsigned int irq)
+{
+	giu_clear(GIUINTENH, 1 << (GPIO_PIN_OF_IRQ(irq) - GIUINT_HIGH_OFFSET));
+}
+
+static void enable_giuint_high_irq(unsigned int irq)
+{
+	giu_set(GIUINTENH, 1 << (GPIO_PIN_OF_IRQ(irq) - GIUINT_HIGH_OFFSET));
+}
+
+#define disable_giuint_high_irq	shutdown_giuint_high_irq
+
+static void ack_giuint_high_irq(unsigned int irq)
+{
+	unsigned int pin;
+
+	pin = GPIO_PIN_OF_IRQ(irq) - GIUINT_HIGH_OFFSET;
+	giu_clear(GIUINTENH, 1 << pin);
+	giu_write(GIUINTSTATH, 1 << pin);
+}
+
+static void end_giuint_high_irq(unsigned int irq)
+{
+	if (!(irq_desc[irq].status & (IRQ_DISABLED | IRQ_INPROGRESS)))
+		giu_set(GIUINTENH, 1 << (GPIO_PIN_OF_IRQ(irq) - GIUINT_HIGH_OFFSET));
+}
+
+static struct hw_interrupt_type giuint_high_irq_type = {
+	.typename	= "GIUINTH",
+	.startup	= startup_giuint_high_irq,
+	.shutdown	= shutdown_giuint_high_irq,
+	.enable		= enable_giuint_high_irq,
+	.disable	= disable_giuint_high_irq,
+	.ack		= ack_giuint_high_irq,
+	.end		= end_giuint_high_irq,
+};
+
+static int giu_get_irq(unsigned int irq, struct pt_regs *regs)
+{
+	uint16_t pendl, pendh, maskl, maskh;
+	int i;
+
+	pendl = giu_read(GIUINTSTATL);
+	pendh = giu_read(GIUINTSTATH);
+	maskl = giu_read(GIUINTENL);
+	maskh = giu_read(GIUINTENH);
+
+	maskl &= pendl;
+	maskh &= pendh;
+
+	if (maskl) {
+		for (i = 0; i < 16; i++) {
+			if (maskl & (1 << i))
+				return GIU_IRQ(i);
+		}
+	} else if (maskh) {
+		for (i = 0; i < 16; i++) {
+			if (maskh & (1 << i))
+				return GIU_IRQ(i + GIUINT_HIGH_OFFSET);
+		}
+	}
+
+	printk(KERN_ERR "spurious GIU interrupt: %04x(%04x),%04x(%04x)\n",
+	       maskl, pendl, maskh, pendh);
+
+	atomic_inc(&irq_err_count);
+
+	return -EINVAL;
+}
+
+void vr41xx_set_irq_trigger(unsigned int pin, irq_trigger_t trigger, irq_signal_t signal)
+{
+	uint16_t mask;
+
+	if (pin < GIUINT_HIGH_OFFSET) {
+		mask = 1 << pin;
+		if (trigger != IRQ_TRIGGER_LEVEL) {
+        		giu_set(GIUINTTYPL, mask);
+			if (signal == IRQ_SIGNAL_HOLD)
+				giu_set(GIUINTHTSELL, mask);
+			else
+				giu_clear(GIUINTHTSELL, mask);
+			if (current_cpu_data.cputype == CPU_VR4133) {
+				switch (trigger) {
+				case IRQ_TRIGGER_EDGE_FALLING:
+					giu_set(GIUFEDGEINHL, mask);
+					giu_clear(GIUREDGEINHL, mask);
+					break;
+				case IRQ_TRIGGER_EDGE_RISING:
+					giu_clear(GIUFEDGEINHL, mask);
+					giu_set(GIUREDGEINHL, mask);
+					break;
+				default:
+					giu_set(GIUFEDGEINHL, mask);
+					giu_set(GIUREDGEINHL, mask);
+					break;
+				}
+			}
+		} else {
+			giu_clear(GIUINTTYPL, mask);
+			giu_clear(GIUINTHTSELL, mask);
+		}
+		giu_write(GIUINTSTATL, mask);
+	} else if (pin < GIUINT_HIGH_MAX) {
+		mask = 1 << (pin - GIUINT_HIGH_OFFSET);
+		if (trigger != IRQ_TRIGGER_LEVEL) {
+			giu_set(GIUINTTYPH, mask);
+			if (signal == IRQ_SIGNAL_HOLD)
+				giu_set(GIUINTHTSELH, mask);
+			else
+				giu_clear(GIUINTHTSELH, mask);
+			if (current_cpu_data.cputype == CPU_VR4133) {
+				switch (trigger) {
+				case IRQ_TRIGGER_EDGE_FALLING:
+					giu_set(GIUFEDGEINHH, mask);
+					giu_clear(GIUREDGEINHH, mask);
+					break;
+				case IRQ_TRIGGER_EDGE_RISING:
+					giu_clear(GIUFEDGEINHH, mask);
+					giu_set(GIUREDGEINHH, mask);
+					break;
+				default:
+					giu_set(GIUFEDGEINHH, mask);
+					giu_set(GIUREDGEINHH, mask);
+					break;
+				}
+			}
+		} else {
+			giu_clear(GIUINTTYPH, mask);
+			giu_clear(GIUINTHTSELH, mask);
+		}
+		giu_write(GIUINTSTATH, mask);
+	}
+}
+
+EXPORT_SYMBOL_GPL(vr41xx_set_irq_trigger);
+
+void vr41xx_set_irq_level(unsigned int pin, irq_level_t level)
+{
+	uint16_t mask;
+
+	if (pin < GIUINT_HIGH_OFFSET) {
+		mask = 1 << pin;
+		if (level == IRQ_LEVEL_HIGH)
+			giu_set(GIUINTALSELL, mask);
+		else
+			giu_clear(GIUINTALSELL, mask);
+		giu_write(GIUINTSTATL, mask);
+	} else if (pin < GIUINT_HIGH_MAX) {
+		mask = 1 << (pin - GIUINT_HIGH_OFFSET);
+		if (level == IRQ_LEVEL_HIGH)
+			giu_set(GIUINTALSELH, mask);
+		else
+			giu_clear(GIUINTALSELH, mask);
+		giu_write(GIUINTSTATH, mask);
+	}
+}
+
+EXPORT_SYMBOL_GPL(vr41xx_set_irq_level);
+
+gpio_data_t vr41xx_gpio_get_pin(unsigned int pin)
+{
+	uint16_t reg, mask;
+
+	if (pin >= giu_nr_pins)
+		return GPIO_DATA_INVAL;
+
+	if (pin < 16) {
+		reg = giu_read(GIUPIODL);
+		mask = (uint16_t)1 << pin;
+	} else if (pin < 32) {
+		reg = giu_read(GIUPIODH);
+		mask = (uint16_t)1 << (pin - 16);
+	} else if (pin < 48) {
+		reg = giu_read(GIUPODATL);
+		mask = (uint16_t)1 << (pin - 32);
+	} else {
+		reg = giu_read(GIUPODATH);
+		mask = (uint16_t)1 << (pin - 48);
+	}
+
+	if (reg & mask)
+		return GPIO_DATA_HIGH;
+
+	return GPIO_DATA_LOW;
+}
+
+EXPORT_SYMBOL_GPL(vr41xx_gpio_get_pin);
+
+int vr41xx_gpio_set_pin(unsigned int pin, gpio_data_t data)
+{
+	uint16_t offset, mask, reg;
+	unsigned long flags;
+
+	if (pin >= giu_nr_pins)
+		return -EINVAL;
+
+	if (pin < 16) {
+		offset = GIUPIODL;
+		mask = (uint16_t)1 << pin;
+	} else if (pin < 32) {
+		offset = GIUPIODH;
+		mask = (uint16_t)1 << (pin - 16);
+	} else if (pin < 48) {
+		offset = GIUPODATL;
+		mask = (uint16_t)1 << (pin - 32);
+	} else {
+		offset = GIUPODATH;
+		mask = (uint16_t)1 << (pin - 48);
+	}
+
+	spin_lock_irqsave(&giu_lock, flags);
+
+	reg = giu_read(offset);
+	if (data == GPIO_DATA_HIGH)
+		reg |= mask;
+	else
+		reg &= ~mask;
+	giu_write(offset, reg);
+
+	spin_unlock_irqrestore(&giu_lock, flags);
+
+	return 0;
+}
+
+EXPORT_SYMBOL_GPL(vr41xx_gpio_set_pin);
+
+int vr41xx_gpio_set_direction(unsigned int pin, gpio_direction_t dir)
+{
+	uint16_t offset, mask, reg;
+	unsigned long flags;
+
+	if (pin >= giu_nr_pins)
+		return -EINVAL;
+
+	if (pin < 16) {
+		offset = GIUIOSELL;
+		mask = (uint16_t)1 << pin;
+	} else if (pin < 32) {
+		offset = GIUIOSELH;
+		mask = (uint16_t)1 << (pin - 16);
+	} else {
+		if (giu_flags & GPIO_HAS_OUTPUT_ENABLE) {
+			offset = GIUPODATEN;
+			mask = (uint16_t)1 << (pin - 32);
+		} else {
+			switch (pin) {
+			case 48:
+				offset = GIUPODATH;
+				mask = PIOEN0;
+				break;
+			case 49:
+				offset = GIUPODATH;
+				mask = PIOEN1;
+				break;
+			default:
+				return -EINVAL;
+			}
+		}
+	}
+
+	spin_lock_irqsave(&giu_lock, flags);
+
+	reg = giu_read(offset);
+	if (dir == GPIO_OUTPUT)
+		reg |= mask;
+	else
+		reg &= ~mask;
+	giu_write(offset, reg);
+
+	spin_unlock_irqrestore(&giu_lock, flags);
+
+	return 0;
+}
+
+EXPORT_SYMBOL_GPL(vr41xx_gpio_set_direction);
+
+int vr41xx_gpio_pullupdown(unsigned int pin, gpio_pull_t pull)
+{
+	uint16_t reg, mask;
+	unsigned long flags;
+
+	if ((giu_flags & GPIO_HAS_PULLUPDOWN_IO) != GPIO_HAS_PULLUPDOWN_IO)
+		return -EPERM;
+
+	if (pin >= 15)
+		return -EINVAL;
+
+	mask = (uint16_t)1 << pin;
+
+	spin_lock_irqsave(&giu_lock, flags);
+
+	if (pull == GPIO_PULL_UP || pull == GPIO_PULL_DOWN) {
+		reg = giu_read(GIUTERMUPDN);
+		if (pull == GPIO_PULL_UP)
+			reg |= mask;
+		else
+			reg &= ~mask;
+		giu_write(GIUTERMUPDN, reg);
+
+		reg = giu_read(GIUUSEUPDN);
+		reg |= mask;
+		giu_write(GIUUSEUPDN, reg);
+	} else {
+		reg = giu_read(GIUUSEUPDN);
+		reg &= ~mask;
+		giu_write(GIUUSEUPDN, reg);
+	}
+
+	spin_unlock_irqrestore(&giu_lock, flags);
+
+	return 0;
+}
+
+EXPORT_SYMBOL_GPL(vr41xx_gpio_pullupdown);
+
+static ssize_t gpio_read(struct file *file, char __user *buf, size_t len,
+                         loff_t *ppos)
+{
+	unsigned int pin;
+	char value = '0';
+
+	pin = iminor(file->f_dentry->d_inode);
+	if (pin >= giu_nr_pins)
+		return -EBADF;
+
+	if (vr41xx_gpio_get_pin(pin) == GPIO_DATA_HIGH)
+		value = '1';
+
+	if (len <= 0)
+		return -EFAULT;
+
+	if (put_user(value, buf))
+		return -EFAULT;
+
+	return 1;
+}
+
+static ssize_t gpio_write(struct file *file, const char __user *data,
+                          size_t len, loff_t *ppos)
+{
+	unsigned int pin;
+	size_t i;
+	char c;
+	int retval = 0;
+
+	pin = iminor(file->f_dentry->d_inode);
+	if (pin >= giu_nr_pins)
+		return -EBADF;
+
+	for (i = 0; i < len; i++) {
+		if (get_user(c, data + i))
+			return -EFAULT;
+
+		switch (c) {
+		case '0':
+			retval = vr41xx_gpio_set_pin(pin, GPIO_DATA_LOW);
+			break;
+		case '1':
+			retval = vr41xx_gpio_set_pin(pin, GPIO_DATA_HIGH);
+			break;
+		case 'D':
+			printk(KERN_INFO "GPIO%d: pull down\n", pin);
+			retval = vr41xx_gpio_pullupdown(pin, GPIO_PULL_DOWN);
+			break;
+		case 'd':
+			printk(KERN_INFO "GPIO%d: pull up/down disable\n", pin);
+			retval = vr41xx_gpio_pullupdown(pin, GPIO_PULL_DISABLE);
+			break;
+		case 'I':
+			printk(KERN_INFO "GPIO%d: input\n", pin);
+			retval = vr41xx_gpio_set_direction(pin, GPIO_INPUT);
+			break;
+		case 'O':
+			printk(KERN_INFO "GPIO%d: output\n", pin);
+			retval = vr41xx_gpio_set_direction(pin, GPIO_OUTPUT);
+			break;
+		case 'o':
+			printk(KERN_INFO "GPIO%d: output disable\n", pin);
+			retval = vr41xx_gpio_set_direction(pin, GPIO_OUTPUT_DISABLE);
+			break;
+		case 'P':
+			printk(KERN_INFO "GPIO%d: pull up\n", pin);
+			retval = vr41xx_gpio_pullupdown(pin, GPIO_PULL_UP);
+			break;
+		case 'p':
+			printk(KERN_INFO "GPIO%d: pull up/down disable\n", pin);
+			retval = vr41xx_gpio_pullupdown(pin, GPIO_PULL_DISABLE);
+			break;
+		default:
+			break;
+		}
+
+		if (retval < 0)
+			break;
+	}
+
+	return i;
+}
+
+static int gpio_open(struct inode *inode, struct file *file)
+{
+	unsigned int pin;
+
+	pin = iminor(inode);
+	if (pin >= giu_nr_pins)
+		return -EBADF;
+
+	return nonseekable_open(inode, file);
+}
+
+static int gpio_release(struct inode *inode, struct file *file)
+{
+	unsigned int pin;
+
+	pin = iminor(inode);
+	if (pin >= giu_nr_pins)
+		return -EBADF;
+
+	return 0;
+}
+
+static struct file_operations gpio_fops = {
+	.owner		= THIS_MODULE,
+	.read		= gpio_read,
+	.write		= gpio_write,
+	.open		= gpio_open,
+	.release	= gpio_release,
+};
+
+static int giu_probe(struct device *dev)
+{
+	unsigned long start, size, flags = 0;
+	unsigned int nr_pins = 0;
+	struct resource *res1, *res2 = NULL;
+	void *base;
+	int retval, i;
+
+	switch (current_cpu_data.cputype) {
+	case CPU_VR4111:
+	case CPU_VR4121:
+		start = GIU_TYPE1_START;
+		size = GIU_TYPE1_SIZE;
+		flags = GPIO_HAS_PULLUPDOWN_IO;
+		nr_pins = 50;
+		break;
+	case CPU_VR4122:
+	case CPU_VR4131:
+		start = GIU_TYPE2_START;
+		size = GIU_TYPE2_SIZE;
+		nr_pins = 36;
+		break;
+	case CPU_VR4133:
+		start = GIU_TYPE3_START;
+		size = GIU_TYPE3_SIZE;
+		flags = GPIO_HAS_INTERRUPT_EDGE_SELECT;
+		nr_pins = 48;
+		break;
+	default:
+		return -ENODEV;
+	}
+
+	res1 = request_mem_region(start, size, "GIU");
+	if (res1 == NULL)
+		return -EBUSY;
+
+	base = ioremap(start, size);
+	if (base == NULL) {
+		release_resource(res1);
+		return -ENOMEM;
+	}
+
+	if (flags & GPIO_HAS_PULLUPDOWN_IO) {
+		res2 = request_mem_region(GIU_PULLUPDOWN_START, GIU_PULLUPDOWN_SIZE, "GIU");
+		if (res2 == NULL) {
+			iounmap(base);
+			release_resource(res1);
+			return -EBUSY;
+		}
+	}
+
+	retval = register_chrdev(major, "GIU", &gpio_fops);
+	if (retval < 0) {
+		iounmap(base);
+		release_resource(res1);
+		release_resource(res2);
+		return retval;
+	}
+
+	if (major == 0) {
+		major = retval;
+		printk(KERN_INFO "GIU: major number %d\n", major);
+	}
+
+	spin_lock_init(&giu_lock);
+	giu_base = base;
+	giu_resource1 = res1;
+	giu_resource2 = res2;
+	giu_flags = flags;
+	giu_nr_pins = nr_pins;
+
+	giu_write(GIUINTENL, 0);
+	giu_write(GIUINTENH, 0);
+
+	for (i = GIU_IRQ_BASE; i <= GIU_IRQ_LAST; i++) {
+		if (i < GIU_IRQ(GIUINT_HIGH_OFFSET))
+			irq_desc[i].handler = &giuint_low_irq_type;
+		else
+			irq_desc[i].handler = &giuint_high_irq_type;
+	}
+
+	return cascade_irq(GIUINT_IRQ, giu_get_irq);
+}
+
+static int giu_remove(struct device *dev)
+{
+	iounmap(giu_base);
+
+	release_resource(giu_resource1);
+	if (giu_flags & GPIO_HAS_PULLUPDOWN_IO)
+		release_resource(giu_resource2);
+
+	return 0;
+}
+
+static struct platform_device *giu_platform_device;
+
+static struct device_driver giu_device_driver = {
+	.name		= "GIU",
+	.bus		= &platform_bus_type,
+	.probe		= giu_probe,
+	.remove		= giu_remove,
+};
+
+static int __devinit vr41xx_giu_init(void)
+{
+	int retval;
+
+	giu_platform_device = platform_device_register_simple("GIU", -1, NULL, 0);
+	if (IS_ERR(giu_platform_device))
+		return PTR_ERR(giu_platform_device);
+
+	retval = driver_register(&giu_device_driver);
+	if (retval < 0)
+		platform_device_unregister(giu_platform_device);
+
+	return retval;
+}
+
+static void __devexit vr41xx_giu_exit(void)
+{
+	driver_unregister(&giu_device_driver);
+
+	platform_device_unregister(giu_platform_device);
+}
+
+module_init(vr41xx_giu_init);
+module_exit(vr41xx_giu_exit);
diff --git a/drivers/ide/Kconfig b/drivers/ide/Kconfig
index 3ac0a53..0273f12 100644
--- a/drivers/ide/Kconfig
+++ b/drivers/ide/Kconfig
@@ -672,8 +672,8 @@
 	  chipsets.
 
 config BLK_DEV_SGIIOC4
-	tristate "Silicon Graphics IOC4 chipset support"
-	depends on IA64_SGI_SN2 || IA64_GENERIC
+	tristate "Silicon Graphics IOC4 chipset ATA/ATAPI support"
+	depends on (IA64_SGI_SN2 || IA64_GENERIC) && SGI_IOC4
 	help
 	  This driver adds PIO & MultiMode DMA-2 support for the SGI IOC4
 	  chipset, which has one channel and can support two devices.
diff --git a/drivers/ide/pci/sgiioc4.c b/drivers/ide/pci/sgiioc4.c
index 4651a22..af526b6 100644
--- a/drivers/ide/pci/sgiioc4.c
+++ b/drivers/ide/pci/sgiioc4.c
@@ -34,7 +34,7 @@
 #include <linux/mm.h>
 #include <linux/ioport.h>
 #include <linux/blkdev.h>
-#include <linux/ioc4_common.h>
+#include <linux/ioc4.h>
 #include <asm/io.h>
 
 #include <linux/ide.h>
@@ -715,14 +715,34 @@
 };
 
 int
-ioc4_ide_attach_one(struct pci_dev *dev, const struct pci_device_id *id)
+ioc4_ide_attach_one(struct ioc4_driver_data *idd)
 {
-	return pci_init_sgiioc4(dev, &sgiioc4_chipsets[id->driver_data]);
+	return pci_init_sgiioc4(idd->idd_pdev,
+				&sgiioc4_chipsets[idd->idd_pci_id->driver_data]);
 }
 
+static struct ioc4_submodule ioc4_ide_submodule = {
+	.is_name = "IOC4_ide",
+	.is_owner = THIS_MODULE,
+	.is_probe = ioc4_ide_attach_one,
+/*	.is_remove = ioc4_ide_remove_one,	*/
+};
+
+static int __devinit
+ioc4_ide_init(void)
+{
+	return ioc4_register_submodule(&ioc4_ide_submodule);
+}
+
+static void __devexit
+ioc4_ide_exit(void)
+{
+	ioc4_unregister_submodule(&ioc4_ide_submodule);
+}
+
+module_init(ioc4_ide_init);
+module_exit(ioc4_ide_exit);
 
 MODULE_AUTHOR("Aniket Malatpure - Silicon Graphics Inc. (SGI)");
 MODULE_DESCRIPTION("IDE PCI driver module for SGI IOC4 Base-IO Card");
 MODULE_LICENSE("GPL");
-
-EXPORT_SYMBOL(ioc4_ide_attach_one);
diff --git a/drivers/input/gameport/gameport.c b/drivers/input/gameport/gameport.c
index 9b8ff39..e152d0f 100644
--- a/drivers/input/gameport/gameport.c
+++ b/drivers/input/gameport/gameport.c
@@ -134,7 +134,7 @@
 	}
 
 	gameport_close(gameport);
-	return (cpu_data[_smp_processor_id()].loops_per_jiffy * (unsigned long)HZ / (1000 / 50)) / (tx < 1 ? 1 : tx);
+	return (cpu_data[raw_smp_processor_id()].loops_per_jiffy * (unsigned long)HZ / (1000 / 50)) / (tx < 1 ? 1 : tx);
 
 #else
 
diff --git a/drivers/md/Makefile b/drivers/md/Makefile
index 90de9c1..d3efedf 100644
--- a/drivers/md/Makefile
+++ b/drivers/md/Makefile
@@ -7,6 +7,7 @@
 dm-multipath-objs := dm-hw-handler.o dm-path-selector.o dm-mpath.o
 dm-snapshot-objs := dm-snap.o dm-exception-store.o
 dm-mirror-objs	:= dm-log.o dm-raid1.o
+md-mod-objs     := md.o bitmap.o
 raid6-objs	:= raid6main.o raid6algos.o raid6recov.o raid6tables.o \
 		   raid6int1.o raid6int2.o raid6int4.o \
 		   raid6int8.o raid6int16.o raid6int32.o \
@@ -28,7 +29,7 @@
 obj-$(CONFIG_MD_RAID6)		+= raid6.o xor.o
 obj-$(CONFIG_MD_MULTIPATH)	+= multipath.o
 obj-$(CONFIG_MD_FAULTY)		+= faulty.o
-obj-$(CONFIG_BLK_DEV_MD)	+= md.o
+obj-$(CONFIG_BLK_DEV_MD)	+= md-mod.o
 obj-$(CONFIG_BLK_DEV_DM)	+= dm-mod.o
 obj-$(CONFIG_DM_CRYPT)		+= dm-crypt.o
 obj-$(CONFIG_DM_MULTIPATH)	+= dm-multipath.o dm-round-robin.o
diff --git a/drivers/md/bitmap.c b/drivers/md/bitmap.c
new file mode 100644
index 0000000..95980ad
--- /dev/null
+++ b/drivers/md/bitmap.c
@@ -0,0 +1,1586 @@
+/*
+ * bitmap.c two-level bitmap (C) Peter T. Breuer (ptb@ot.uc3m.es) 2003
+ *
+ * bitmap_create  - sets up the bitmap structure
+ * bitmap_destroy - destroys the bitmap structure
+ *
+ * additions, Copyright (C) 2003-2004, Paul Clements, SteelEye Technology, Inc.:
+ * - added disk storage for bitmap
+ * - changes to allow various bitmap chunk sizes
+ * - added bitmap daemon (to asynchronously clear bitmap bits from disk)
+ */
+
+/*
+ * Still to do:
+ *
+ * flush after percent set rather than just time based. (maybe both).
+ * wait if count gets too high, wake when it drops to half.
+ * allow bitmap to be mirrored with superblock (before or after...)
+ * allow hot-add to re-instate a current device.
+ * allow hot-add of bitmap after quiessing device
+ */
+
+#include <linux/module.h>
+#include <linux/version.h>
+#include <linux/errno.h>
+#include <linux/slab.h>
+#include <linux/init.h>
+#include <linux/config.h>
+#include <linux/timer.h>
+#include <linux/sched.h>
+#include <linux/list.h>
+#include <linux/file.h>
+#include <linux/mount.h>
+#include <linux/buffer_head.h>
+#include <linux/raid/md.h>
+#include <linux/raid/bitmap.h>
+
+/* debug macros */
+
+#define DEBUG 0
+
+#if DEBUG
+/* these are for debugging purposes only! */
+
+/* define one and only one of these */
+#define INJECT_FAULTS_1 0 /* cause bitmap_alloc_page to fail always */
+#define INJECT_FAULTS_2 0 /* cause bitmap file to be kicked when first bit set*/
+#define INJECT_FAULTS_3 0 /* treat bitmap file as kicked at init time */
+#define INJECT_FAULTS_4 0 /* undef */
+#define INJECT_FAULTS_5 0 /* undef */
+#define INJECT_FAULTS_6 0
+
+/* if these are defined, the driver will fail! debug only */
+#define INJECT_FATAL_FAULT_1 0 /* fail kmalloc, causing bitmap_create to fail */
+#define INJECT_FATAL_FAULT_2 0 /* undef */
+#define INJECT_FATAL_FAULT_3 0 /* undef */
+#endif
+
+//#define DPRINTK PRINTK /* set this NULL to avoid verbose debug output */
+#define DPRINTK(x...) do { } while(0)
+
+#ifndef PRINTK
+#  if DEBUG > 0
+#    define PRINTK(x...) printk(KERN_DEBUG x)
+#  else
+#    define PRINTK(x...)
+#  endif
+#endif
+
+static inline char * bmname(struct bitmap *bitmap)
+{
+	return bitmap->mddev ? mdname(bitmap->mddev) : "mdX";
+}
+
+
+/*
+ * test if the bitmap is active
+ */
+int bitmap_active(struct bitmap *bitmap)
+{
+	unsigned long flags;
+	int res = 0;
+
+	if (!bitmap)
+		return res;
+	spin_lock_irqsave(&bitmap->lock, flags);
+	res = bitmap->flags & BITMAP_ACTIVE;
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+	return res;
+}
+
+#define WRITE_POOL_SIZE 256
+/* mempool for queueing pending writes on the bitmap file */
+static void *write_pool_alloc(unsigned int gfp_flags, void *data)
+{
+	return kmalloc(sizeof(struct page_list), gfp_flags);
+}
+
+static void write_pool_free(void *ptr, void *data)
+{
+	kfree(ptr);
+}
+
+/*
+ * just a placeholder - calls kmalloc for bitmap pages
+ */
+static unsigned char *bitmap_alloc_page(struct bitmap *bitmap)
+{
+	unsigned char *page;
+
+#if INJECT_FAULTS_1
+	page = NULL;
+#else
+	page = kmalloc(PAGE_SIZE, GFP_NOIO);
+#endif
+	if (!page)
+		printk("%s: bitmap_alloc_page FAILED\n", bmname(bitmap));
+	else
+		PRINTK("%s: bitmap_alloc_page: allocated page at %p\n",
+			bmname(bitmap), page);
+	return page;
+}
+
+/*
+ * for now just a placeholder -- just calls kfree for bitmap pages
+ */
+static void bitmap_free_page(struct bitmap *bitmap, unsigned char *page)
+{
+	PRINTK("%s: bitmap_free_page: free page %p\n", bmname(bitmap), page);
+	kfree(page);
+}
+
+/*
+ * check a page and, if necessary, allocate it (or hijack it if the alloc fails)
+ *
+ * 1) check to see if this page is allocated, if it's not then try to alloc
+ * 2) if the alloc fails, set the page's hijacked flag so we'll use the
+ *    page pointer directly as a counter
+ *
+ * if we find our page, we increment the page's refcount so that it stays
+ * allocated while we're using it
+ */
+static int bitmap_checkpage(struct bitmap *bitmap, unsigned long page, int create)
+{
+	unsigned char *mappage;
+
+	if (page >= bitmap->pages) {
+		printk(KERN_ALERT
+			"%s: invalid bitmap page request: %lu (> %lu)\n",
+			bmname(bitmap), page, bitmap->pages-1);
+		return -EINVAL;
+	}
+
+
+	if (bitmap->bp[page].hijacked) /* it's hijacked, don't try to alloc */
+		return 0;
+
+	if (bitmap->bp[page].map) /* page is already allocated, just return */
+		return 0;
+
+	if (!create)
+		return -ENOENT;
+
+	spin_unlock_irq(&bitmap->lock);
+
+	/* this page has not been allocated yet */
+
+	if ((mappage = bitmap_alloc_page(bitmap)) == NULL) {
+		PRINTK("%s: bitmap map page allocation failed, hijacking\n",
+			bmname(bitmap));
+		/* failed - set the hijacked flag so that we can use the
+		 * pointer as a counter */
+		spin_lock_irq(&bitmap->lock);
+		if (!bitmap->bp[page].map)
+			bitmap->bp[page].hijacked = 1;
+		goto out;
+	}
+
+	/* got a page */
+
+	spin_lock_irq(&bitmap->lock);
+
+	/* recheck the page */
+
+	if (bitmap->bp[page].map || bitmap->bp[page].hijacked) {
+		/* somebody beat us to getting the page */
+		bitmap_free_page(bitmap, mappage);
+		return 0;
+	}
+
+	/* no page was in place and we have one, so install it */
+
+	memset(mappage, 0, PAGE_SIZE);
+	bitmap->bp[page].map = mappage;
+	bitmap->missing_pages--;
+out:
+	return 0;
+}
+
+
+/* if page is completely empty, put it back on the free list, or dealloc it */
+/* if page was hijacked, unmark the flag so it might get alloced next time */
+/* Note: lock should be held when calling this */
+static inline void bitmap_checkfree(struct bitmap *bitmap, unsigned long page)
+{
+	char *ptr;
+
+	if (bitmap->bp[page].count) /* page is still busy */
+		return;
+
+	/* page is no longer in use, it can be released */
+
+	if (bitmap->bp[page].hijacked) { /* page was hijacked, undo this now */
+		bitmap->bp[page].hijacked = 0;
+		bitmap->bp[page].map = NULL;
+		return;
+	}
+
+	/* normal case, free the page */
+
+#if 0
+/* actually ... let's not.  We will probably need the page again exactly when
+ * memory is tight and we are flusing to disk
+ */
+	return;
+#else
+	ptr = bitmap->bp[page].map;
+	bitmap->bp[page].map = NULL;
+	bitmap->missing_pages++;
+	bitmap_free_page(bitmap, ptr);
+	return;
+#endif
+}
+
+
+/*
+ * bitmap file handling - read and write the bitmap file and its superblock
+ */
+
+/* copy the pathname of a file to a buffer */
+char *file_path(struct file *file, char *buf, int count)
+{
+	struct dentry *d;
+	struct vfsmount *v;
+
+	if (!buf)
+		return NULL;
+
+	d = file->f_dentry;
+	v = file->f_vfsmnt;
+
+	buf = d_path(d, v, buf, count);
+
+	return IS_ERR(buf) ? NULL : buf;
+}
+
+/*
+ * basic page I/O operations
+ */
+
+/* IO operations when bitmap is stored near all superblocks */
+static struct page *read_sb_page(mddev_t *mddev, long offset, unsigned long index)
+{
+	/* choose a good rdev and read the page from there */
+
+	mdk_rdev_t *rdev;
+	struct list_head *tmp;
+	struct page *page = alloc_page(GFP_KERNEL);
+	sector_t target;
+
+	if (!page)
+		return ERR_PTR(-ENOMEM);
+	do {
+		ITERATE_RDEV(mddev, rdev, tmp)
+			if (rdev->in_sync && !rdev->faulty)
+				goto found;
+		return ERR_PTR(-EIO);
+
+	found:
+		target = (rdev->sb_offset << 1) + offset + index * (PAGE_SIZE/512);
+
+	} while (!sync_page_io(rdev->bdev, target, PAGE_SIZE, page, READ));
+
+	page->index = index;
+	return page;
+}
+
+static int write_sb_page(mddev_t *mddev, long offset, struct page *page, int wait)
+{
+	mdk_rdev_t *rdev;
+	struct list_head *tmp;
+
+	ITERATE_RDEV(mddev, rdev, tmp)
+		if (rdev->in_sync && !rdev->faulty)
+			md_super_write(mddev, rdev,
+				       (rdev->sb_offset<<1) + offset
+				       + page->index * (PAGE_SIZE/512),
+				       PAGE_SIZE,
+				       page);
+
+	if (wait)
+		wait_event(mddev->sb_wait, atomic_read(&mddev->pending_writes)==0);
+	return 0;
+}
+
+/*
+ * write out a page to a file
+ */
+static int write_page(struct bitmap *bitmap, struct page *page, int wait)
+{
+	int ret = -ENOMEM;
+
+	if (bitmap->file == NULL)
+		return write_sb_page(bitmap->mddev, bitmap->offset, page, wait);
+
+	if (wait)
+		lock_page(page);
+	else {
+		if (TestSetPageLocked(page))
+			return -EAGAIN; /* already locked */
+		if (PageWriteback(page)) {
+			unlock_page(page);
+			return -EAGAIN;
+		}
+	}
+
+	ret = page->mapping->a_ops->prepare_write(NULL, page, 0, PAGE_SIZE);
+	if (!ret)
+		ret = page->mapping->a_ops->commit_write(NULL, page, 0,
+			PAGE_SIZE);
+	if (ret) {
+		unlock_page(page);
+		return ret;
+	}
+
+	set_page_dirty(page); /* force it to be written out */
+
+	if (!wait) {
+		/* add to list to be waited for by daemon */
+		struct page_list *item = mempool_alloc(bitmap->write_pool, GFP_NOIO);
+		item->page = page;
+		page_cache_get(page);
+		spin_lock(&bitmap->write_lock);
+		list_add(&item->list, &bitmap->complete_pages);
+		spin_unlock(&bitmap->write_lock);
+		md_wakeup_thread(bitmap->writeback_daemon);
+	}
+	return write_one_page(page, wait);
+}
+
+/* read a page from a file, pinning it into cache, and return bytes_read */
+static struct page *read_page(struct file *file, unsigned long index,
+					unsigned long *bytes_read)
+{
+	struct inode *inode = file->f_mapping->host;
+	struct page *page = NULL;
+	loff_t isize = i_size_read(inode);
+	unsigned long end_index = isize >> PAGE_CACHE_SHIFT;
+
+	PRINTK("read bitmap file (%dB @ %Lu)\n", (int)PAGE_CACHE_SIZE,
+			(unsigned long long)index << PAGE_CACHE_SHIFT);
+
+	page = read_cache_page(inode->i_mapping, index,
+			(filler_t *)inode->i_mapping->a_ops->readpage, file);
+	if (IS_ERR(page))
+		goto out;
+	wait_on_page_locked(page);
+	if (!PageUptodate(page) || PageError(page)) {
+		page_cache_release(page);
+		page = ERR_PTR(-EIO);
+		goto out;
+	}
+
+	if (index > end_index) /* we have read beyond EOF */
+		*bytes_read = 0;
+	else if (index == end_index) /* possible short read */
+		*bytes_read = isize & ~PAGE_CACHE_MASK;
+	else
+		*bytes_read = PAGE_CACHE_SIZE; /* got a full page */
+out:
+	if (IS_ERR(page))
+		printk(KERN_ALERT "md: bitmap read error: (%dB @ %Lu): %ld\n",
+			(int)PAGE_CACHE_SIZE,
+			(unsigned long long)index << PAGE_CACHE_SHIFT,
+			PTR_ERR(page));
+	return page;
+}
+
+/*
+ * bitmap file superblock operations
+ */
+
+/* update the event counter and sync the superblock to disk */
+int bitmap_update_sb(struct bitmap *bitmap)
+{
+	bitmap_super_t *sb;
+	unsigned long flags;
+
+	if (!bitmap || !bitmap->mddev) /* no bitmap for this array */
+		return 0;
+	spin_lock_irqsave(&bitmap->lock, flags);
+	if (!bitmap->sb_page) { /* no superblock */
+		spin_unlock_irqrestore(&bitmap->lock, flags);
+		return 0;
+	}
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+	sb = (bitmap_super_t *)kmap(bitmap->sb_page);
+	sb->events = cpu_to_le64(bitmap->mddev->events);
+	if (!bitmap->mddev->degraded)
+		sb->events_cleared = cpu_to_le64(bitmap->mddev->events);
+	kunmap(bitmap->sb_page);
+	return write_page(bitmap, bitmap->sb_page, 1);
+}
+
+/* print out the bitmap file superblock */
+void bitmap_print_sb(struct bitmap *bitmap)
+{
+	bitmap_super_t *sb;
+
+	if (!bitmap || !bitmap->sb_page)
+		return;
+	sb = (bitmap_super_t *)kmap(bitmap->sb_page);
+	printk(KERN_DEBUG "%s: bitmap file superblock:\n", bmname(bitmap));
+	printk(KERN_DEBUG "         magic: %08x\n", le32_to_cpu(sb->magic));
+	printk(KERN_DEBUG "       version: %d\n", le32_to_cpu(sb->version));
+	printk(KERN_DEBUG "          uuid: %08x.%08x.%08x.%08x\n",
+					*(__u32 *)(sb->uuid+0),
+					*(__u32 *)(sb->uuid+4),
+					*(__u32 *)(sb->uuid+8),
+					*(__u32 *)(sb->uuid+12));
+	printk(KERN_DEBUG "        events: %llu\n",
+			(unsigned long long) le64_to_cpu(sb->events));
+	printk(KERN_DEBUG "events cleared: %llu\n",
+			(unsigned long long) le64_to_cpu(sb->events_cleared));
+	printk(KERN_DEBUG "         state: %08x\n", le32_to_cpu(sb->state));
+	printk(KERN_DEBUG "     chunksize: %d B\n", le32_to_cpu(sb->chunksize));
+	printk(KERN_DEBUG "  daemon sleep: %ds\n", le32_to_cpu(sb->daemon_sleep));
+	printk(KERN_DEBUG "     sync size: %llu KB\n",
+			(unsigned long long)le64_to_cpu(sb->sync_size)/2);
+	kunmap(bitmap->sb_page);
+}
+
+/* read the superblock from the bitmap file and initialize some bitmap fields */
+static int bitmap_read_sb(struct bitmap *bitmap)
+{
+	char *reason = NULL;
+	bitmap_super_t *sb;
+	unsigned long chunksize, daemon_sleep;
+	unsigned long bytes_read;
+	unsigned long long events;
+	int err = -EINVAL;
+
+	/* page 0 is the superblock, read it... */
+	if (bitmap->file)
+		bitmap->sb_page = read_page(bitmap->file, 0, &bytes_read);
+	else {
+		bitmap->sb_page = read_sb_page(bitmap->mddev, bitmap->offset, 0);
+		bytes_read = PAGE_SIZE;
+	}
+	if (IS_ERR(bitmap->sb_page)) {
+		err = PTR_ERR(bitmap->sb_page);
+		bitmap->sb_page = NULL;
+		return err;
+	}
+
+	sb = (bitmap_super_t *)kmap(bitmap->sb_page);
+
+	if (bytes_read < sizeof(*sb)) { /* short read */
+		printk(KERN_INFO "%s: bitmap file superblock truncated\n",
+			bmname(bitmap));
+		err = -ENOSPC;
+		goto out;
+	}
+
+	chunksize = le32_to_cpu(sb->chunksize);
+	daemon_sleep = le32_to_cpu(sb->daemon_sleep);
+
+	/* verify that the bitmap-specific fields are valid */
+	if (sb->magic != cpu_to_le32(BITMAP_MAGIC))
+		reason = "bad magic";
+	else if (sb->version != cpu_to_le32(BITMAP_MAJOR))
+		reason = "unrecognized superblock version";
+	else if (chunksize < 512 || chunksize > (1024 * 1024 * 4))
+		reason = "bitmap chunksize out of range (512B - 4MB)";
+	else if ((1 << ffz(~chunksize)) != chunksize)
+		reason = "bitmap chunksize not a power of 2";
+	else if (daemon_sleep < 1 || daemon_sleep > 15)
+		reason = "daemon sleep period out of range";
+	if (reason) {
+		printk(KERN_INFO "%s: invalid bitmap file superblock: %s\n",
+			bmname(bitmap), reason);
+		goto out;
+	}
+
+	/* keep the array size field of the bitmap superblock up to date */
+	sb->sync_size = cpu_to_le64(bitmap->mddev->resync_max_sectors);
+
+	if (!bitmap->mddev->persistent)
+		goto success;
+
+	/*
+	 * if we have a persistent array superblock, compare the
+	 * bitmap's UUID and event counter to the mddev's
+	 */
+	if (memcmp(sb->uuid, bitmap->mddev->uuid, 16)) {
+		printk(KERN_INFO "%s: bitmap superblock UUID mismatch\n",
+			bmname(bitmap));
+		goto out;
+	}
+	events = le64_to_cpu(sb->events);
+	if (events < bitmap->mddev->events) {
+		printk(KERN_INFO "%s: bitmap file is out of date (%llu < %llu) "
+			"-- forcing full recovery\n", bmname(bitmap), events,
+			(unsigned long long) bitmap->mddev->events);
+		sb->state |= BITMAP_STALE;
+	}
+success:
+	/* assign fields using values from superblock */
+	bitmap->chunksize = chunksize;
+	bitmap->daemon_sleep = daemon_sleep;
+	bitmap->flags |= sb->state;
+	bitmap->events_cleared = le64_to_cpu(sb->events_cleared);
+	err = 0;
+out:
+	kunmap(bitmap->sb_page);
+	if (err)
+		bitmap_print_sb(bitmap);
+	return err;
+}
+
+enum bitmap_mask_op {
+	MASK_SET,
+	MASK_UNSET
+};
+
+/* record the state of the bitmap in the superblock */
+static void bitmap_mask_state(struct bitmap *bitmap, enum bitmap_state bits,
+				enum bitmap_mask_op op)
+{
+	bitmap_super_t *sb;
+	unsigned long flags;
+
+	spin_lock_irqsave(&bitmap->lock, flags);
+	if (!bitmap || !bitmap->sb_page) { /* can't set the state */
+		spin_unlock_irqrestore(&bitmap->lock, flags);
+		return;
+	}
+	page_cache_get(bitmap->sb_page);
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+	sb = (bitmap_super_t *)kmap(bitmap->sb_page);
+	switch (op) {
+		case MASK_SET: sb->state |= bits;
+				break;
+		case MASK_UNSET: sb->state &= ~bits;
+				break;
+		default: BUG();
+	}
+	kunmap(bitmap->sb_page);
+	page_cache_release(bitmap->sb_page);
+}
+
+/*
+ * general bitmap file operations
+ */
+
+/* calculate the index of the page that contains this bit */
+static inline unsigned long file_page_index(unsigned long chunk)
+{
+	return CHUNK_BIT_OFFSET(chunk) >> PAGE_BIT_SHIFT;
+}
+
+/* calculate the (bit) offset of this bit within a page */
+static inline unsigned long file_page_offset(unsigned long chunk)
+{
+	return CHUNK_BIT_OFFSET(chunk) & (PAGE_BITS - 1);
+}
+
+/*
+ * return a pointer to the page in the filemap that contains the given bit
+ *
+ * this lookup is complicated by the fact that the bitmap sb might be exactly
+ * 1 page (e.g., x86) or less than 1 page -- so the bitmap might start on page
+ * 0 or page 1
+ */
+static inline struct page *filemap_get_page(struct bitmap *bitmap,
+					unsigned long chunk)
+{
+	return bitmap->filemap[file_page_index(chunk) - file_page_index(0)];
+}
+
+
+static void bitmap_file_unmap(struct bitmap *bitmap)
+{
+	struct page **map, *sb_page;
+	unsigned long *attr;
+	int pages;
+	unsigned long flags;
+
+	spin_lock_irqsave(&bitmap->lock, flags);
+	map = bitmap->filemap;
+	bitmap->filemap = NULL;
+	attr = bitmap->filemap_attr;
+	bitmap->filemap_attr = NULL;
+	pages = bitmap->file_pages;
+	bitmap->file_pages = 0;
+	sb_page = bitmap->sb_page;
+	bitmap->sb_page = NULL;
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+
+	while (pages--)
+		if (map[pages]->index != 0) /* 0 is sb_page, release it below */
+			page_cache_release(map[pages]);
+	kfree(map);
+	kfree(attr);
+
+	if (sb_page)
+		page_cache_release(sb_page);
+}
+
+static void bitmap_stop_daemons(struct bitmap *bitmap);
+
+/* dequeue the next item in a page list -- don't call from irq context */
+static struct page_list *dequeue_page(struct bitmap *bitmap)
+{
+	struct page_list *item = NULL;
+	struct list_head *head = &bitmap->complete_pages;
+
+	spin_lock(&bitmap->write_lock);
+	if (list_empty(head))
+		goto out;
+	item = list_entry(head->prev, struct page_list, list);
+	list_del(head->prev);
+out:
+	spin_unlock(&bitmap->write_lock);
+	return item;
+}
+
+static void drain_write_queues(struct bitmap *bitmap)
+{
+	struct page_list *item;
+
+	while ((item = dequeue_page(bitmap))) {
+		/* don't bother to wait */
+		page_cache_release(item->page);
+		mempool_free(item, bitmap->write_pool);
+	}
+
+	wake_up(&bitmap->write_wait);
+}
+
+static void bitmap_file_put(struct bitmap *bitmap)
+{
+	struct file *file;
+	struct inode *inode;
+	unsigned long flags;
+
+	spin_lock_irqsave(&bitmap->lock, flags);
+	file = bitmap->file;
+	bitmap->file = NULL;
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+
+	bitmap_stop_daemons(bitmap);
+
+	drain_write_queues(bitmap);
+
+	bitmap_file_unmap(bitmap);
+
+	if (file) {
+		inode = file->f_mapping->host;
+		spin_lock(&inode->i_lock);
+		atomic_set(&inode->i_writecount, 1); /* allow writes again */
+		spin_unlock(&inode->i_lock);
+		fput(file);
+	}
+}
+
+
+/*
+ * bitmap_file_kick - if an error occurs while manipulating the bitmap file
+ * then it is no longer reliable, so we stop using it and we mark the file
+ * as failed in the superblock
+ */
+static void bitmap_file_kick(struct bitmap *bitmap)
+{
+	char *path, *ptr = NULL;
+
+	bitmap_mask_state(bitmap, BITMAP_STALE, MASK_SET);
+	bitmap_update_sb(bitmap);
+
+	if (bitmap->file) {
+		path = kmalloc(PAGE_SIZE, GFP_KERNEL);
+		if (path)
+			ptr = file_path(bitmap->file, path, PAGE_SIZE);
+
+		printk(KERN_ALERT "%s: kicking failed bitmap file %s from array!\n",
+		       bmname(bitmap), ptr ? ptr : "");
+
+		kfree(path);
+	}
+
+	bitmap_file_put(bitmap);
+
+	return;
+}
+
+enum bitmap_page_attr {
+	BITMAP_PAGE_DIRTY = 1, // there are set bits that need to be synced
+	BITMAP_PAGE_CLEAN = 2, // there are bits that might need to be cleared
+	BITMAP_PAGE_NEEDWRITE=4, // there are cleared bits that need to be synced
+};
+
+static inline void set_page_attr(struct bitmap *bitmap, struct page *page,
+				enum bitmap_page_attr attr)
+{
+	bitmap->filemap_attr[page->index] |= attr;
+}
+
+static inline void clear_page_attr(struct bitmap *bitmap, struct page *page,
+				enum bitmap_page_attr attr)
+{
+	bitmap->filemap_attr[page->index] &= ~attr;
+}
+
+static inline unsigned long get_page_attr(struct bitmap *bitmap, struct page *page)
+{
+	return bitmap->filemap_attr[page->index];
+}
+
+/*
+ * bitmap_file_set_bit -- called before performing a write to the md device
+ * to set (and eventually sync) a particular bit in the bitmap file
+ *
+ * we set the bit immediately, then we record the page number so that
+ * when an unplug occurs, we can flush the dirty pages out to disk
+ */
+static void bitmap_file_set_bit(struct bitmap *bitmap, sector_t block)
+{
+	unsigned long bit;
+	struct page *page;
+	void *kaddr;
+	unsigned long chunk = block >> CHUNK_BLOCK_SHIFT(bitmap);
+
+	if (!bitmap->filemap) {
+		return;
+	}
+
+	page = filemap_get_page(bitmap, chunk);
+	bit = file_page_offset(chunk);
+
+
+	/* make sure the page stays cached until it gets written out */
+	if (! (get_page_attr(bitmap, page) & BITMAP_PAGE_DIRTY))
+		page_cache_get(page);
+
+ 	/* set the bit */
+	kaddr = kmap_atomic(page, KM_USER0);
+	set_bit(bit, kaddr);
+	kunmap_atomic(kaddr, KM_USER0);
+	PRINTK("set file bit %lu page %lu\n", bit, page->index);
+
+	/* record page number so it gets flushed to disk when unplug occurs */
+	set_page_attr(bitmap, page, BITMAP_PAGE_DIRTY);
+
+}
+
+/* this gets called when the md device is ready to unplug its underlying
+ * (slave) device queues -- before we let any writes go down, we need to
+ * sync the dirty pages of the bitmap file to disk */
+int bitmap_unplug(struct bitmap *bitmap)
+{
+	unsigned long i, attr, flags;
+	struct page *page;
+	int wait = 0;
+	int err;
+
+	if (!bitmap)
+		return 0;
+
+	/* look at each page to see if there are any set bits that need to be
+	 * flushed out to disk */
+	for (i = 0; i < bitmap->file_pages; i++) {
+		spin_lock_irqsave(&bitmap->lock, flags);
+		if (!bitmap->filemap) {
+			spin_unlock_irqrestore(&bitmap->lock, flags);
+			return 0;
+		}
+		page = bitmap->filemap[i];
+		attr = get_page_attr(bitmap, page);
+		clear_page_attr(bitmap, page, BITMAP_PAGE_DIRTY);
+		clear_page_attr(bitmap, page, BITMAP_PAGE_NEEDWRITE);
+		if ((attr & BITMAP_PAGE_DIRTY))
+			wait = 1;
+		spin_unlock_irqrestore(&bitmap->lock, flags);
+
+		if (attr & (BITMAP_PAGE_DIRTY | BITMAP_PAGE_NEEDWRITE)) {
+			err = write_page(bitmap, page, 0);
+			if (err == -EAGAIN) {
+				if (attr & BITMAP_PAGE_DIRTY)
+					err = write_page(bitmap, page, 1);
+				else
+					err = 0;
+			}
+			if (err)
+				return 1;
+		}
+	}
+	if (wait) { /* if any writes were performed, we need to wait on them */
+		if (bitmap->file) {
+			spin_lock_irq(&bitmap->write_lock);
+			wait_event_lock_irq(bitmap->write_wait,
+					    list_empty(&bitmap->complete_pages), bitmap->write_lock,
+					    wake_up_process(bitmap->writeback_daemon->tsk));
+			spin_unlock_irq(&bitmap->write_lock);
+		} else
+			wait_event(bitmap->mddev->sb_wait,
+				   atomic_read(&bitmap->mddev->pending_writes)==0);
+	}
+	return 0;
+}
+
+static void bitmap_set_memory_bits(struct bitmap *bitmap, sector_t offset,
+	unsigned long sectors, int in_sync);
+/* * bitmap_init_from_disk -- called at bitmap_create time to initialize
+ * the in-memory bitmap from the on-disk bitmap -- also, sets up the
+ * memory mapping of the bitmap file
+ * Special cases:
+ *   if there's no bitmap file, or if the bitmap file had been
+ *   previously kicked from the array, we mark all the bits as
+ *   1's in order to cause a full resync.
+ */
+static int bitmap_init_from_disk(struct bitmap *bitmap, int in_sync)
+{
+	unsigned long i, chunks, index, oldindex, bit;
+	struct page *page = NULL, *oldpage = NULL;
+	unsigned long num_pages, bit_cnt = 0;
+	struct file *file;
+	unsigned long bytes, offset, dummy;
+	int outofdate;
+	int ret = -ENOSPC;
+
+	chunks = bitmap->chunks;
+	file = bitmap->file;
+
+	BUG_ON(!file && !bitmap->offset);
+
+#if INJECT_FAULTS_3
+	outofdate = 1;
+#else
+	outofdate = bitmap->flags & BITMAP_STALE;
+#endif
+	if (outofdate)
+		printk(KERN_INFO "%s: bitmap file is out of date, doing full "
+			"recovery\n", bmname(bitmap));
+
+	bytes = (chunks + 7) / 8;
+
+	num_pages = (bytes + sizeof(bitmap_super_t) + PAGE_SIZE - 1) / PAGE_SIZE;
+
+	if (file && i_size_read(file->f_mapping->host) < bytes + sizeof(bitmap_super_t)) {
+		printk(KERN_INFO "%s: bitmap file too short %lu < %lu\n",
+			bmname(bitmap),
+			(unsigned long) i_size_read(file->f_mapping->host),
+			bytes + sizeof(bitmap_super_t));
+		goto out;
+	}
+
+	ret = -ENOMEM;
+
+	bitmap->filemap = kmalloc(sizeof(struct page *) * num_pages, GFP_KERNEL);
+	if (!bitmap->filemap)
+		goto out;
+
+	bitmap->filemap_attr = kmalloc(sizeof(long) * num_pages, GFP_KERNEL);
+	if (!bitmap->filemap_attr)
+		goto out;
+
+	memset(bitmap->filemap_attr, 0, sizeof(long) * num_pages);
+
+	oldindex = ~0L;
+
+	for (i = 0; i < chunks; i++) {
+		index = file_page_index(i);
+		bit = file_page_offset(i);
+		if (index != oldindex) { /* this is a new page, read it in */
+			/* unmap the old page, we're done with it */
+			if (oldpage != NULL)
+				kunmap(oldpage);
+			if (index == 0) {
+				/*
+				 * if we're here then the superblock page
+				 * contains some bits (PAGE_SIZE != sizeof sb)
+				 * we've already read it in, so just use it
+				 */
+				page = bitmap->sb_page;
+				offset = sizeof(bitmap_super_t);
+			} else if (file) {
+				page = read_page(file, index, &dummy);
+				offset = 0;
+			} else {
+				page = read_sb_page(bitmap->mddev, bitmap->offset, index);
+				offset = 0;
+			}
+			if (IS_ERR(page)) { /* read error */
+				ret = PTR_ERR(page);
+				goto out;
+			}
+
+			oldindex = index;
+			oldpage = page;
+			kmap(page);
+
+			if (outofdate) {
+				/*
+				 * if bitmap is out of date, dirty the
+			 	 * whole page and write it out
+				 */
+				memset(page_address(page) + offset, 0xff,
+					PAGE_SIZE - offset);
+				ret = write_page(bitmap, page, 1);
+				if (ret) {
+					kunmap(page);
+					/* release, page not in filemap yet */
+					page_cache_release(page);
+					goto out;
+				}
+			}
+
+			bitmap->filemap[bitmap->file_pages++] = page;
+		}
+		if (test_bit(bit, page_address(page))) {
+			/* if the disk bit is set, set the memory bit */
+			bitmap_set_memory_bits(bitmap,
+					i << CHUNK_BLOCK_SHIFT(bitmap), 1, in_sync);
+			bit_cnt++;
+		}
+	}
+
+ 	/* everything went OK */
+	ret = 0;
+	bitmap_mask_state(bitmap, BITMAP_STALE, MASK_UNSET);
+
+	if (page) /* unmap the last page */
+		kunmap(page);
+
+	if (bit_cnt) { /* Kick recovery if any bits were set */
+		set_bit(MD_RECOVERY_NEEDED, &bitmap->mddev->recovery);
+		md_wakeup_thread(bitmap->mddev->thread);
+	}
+
+out:
+	printk(KERN_INFO "%s: bitmap initialized from disk: "
+		"read %lu/%lu pages, set %lu bits, status: %d\n",
+		bmname(bitmap), bitmap->file_pages, num_pages, bit_cnt, ret);
+
+	return ret;
+}
+
+void bitmap_write_all(struct bitmap *bitmap)
+{
+	/* We don't actually write all bitmap blocks here,
+	 * just flag them as needing to be written
+	 */
+
+	unsigned long chunks = bitmap->chunks;
+	unsigned long bytes = (chunks+7)/8 + sizeof(bitmap_super_t);
+	unsigned long num_pages = (bytes + PAGE_SIZE-1) / PAGE_SIZE;
+	while (num_pages--)
+		bitmap->filemap_attr[num_pages] |= BITMAP_PAGE_NEEDWRITE;
+}
+
+
+static void bitmap_count_page(struct bitmap *bitmap, sector_t offset, int inc)
+{
+	sector_t chunk = offset >> CHUNK_BLOCK_SHIFT(bitmap);
+	unsigned long page = chunk >> PAGE_COUNTER_SHIFT;
+	bitmap->bp[page].count += inc;
+/*
+	if (page == 0) printk("count page 0, offset %llu: %d gives %d\n",
+			      (unsigned long long)offset, inc, bitmap->bp[page].count);
+*/
+	bitmap_checkfree(bitmap, page);
+}
+static bitmap_counter_t *bitmap_get_counter(struct bitmap *bitmap,
+					    sector_t offset, int *blocks,
+					    int create);
+
+/*
+ * bitmap daemon -- periodically wakes up to clean bits and flush pages
+ *			out to disk
+ */
+
+int bitmap_daemon_work(struct bitmap *bitmap)
+{
+	unsigned long j;
+	unsigned long flags;
+	struct page *page = NULL, *lastpage = NULL;
+	int err = 0;
+	int blocks;
+	int attr;
+
+	if (bitmap == NULL)
+		return 0;
+	if (time_before(jiffies, bitmap->daemon_lastrun + bitmap->daemon_sleep*HZ))
+		return 0;
+	bitmap->daemon_lastrun = jiffies;
+
+	for (j = 0; j < bitmap->chunks; j++) {
+		bitmap_counter_t *bmc;
+		spin_lock_irqsave(&bitmap->lock, flags);
+		if (!bitmap->filemap) {
+			/* error or shutdown */
+			spin_unlock_irqrestore(&bitmap->lock, flags);
+			break;
+		}
+
+		page = filemap_get_page(bitmap, j);
+
+		if (page != lastpage) {
+			/* skip this page unless it's marked as needing cleaning */
+			if (!((attr=get_page_attr(bitmap, page)) & BITMAP_PAGE_CLEAN)) {
+				if (attr & BITMAP_PAGE_NEEDWRITE) {
+					page_cache_get(page);
+					clear_page_attr(bitmap, page, BITMAP_PAGE_NEEDWRITE);
+				}
+				spin_unlock_irqrestore(&bitmap->lock, flags);
+				if (attr & BITMAP_PAGE_NEEDWRITE) {
+					switch (write_page(bitmap, page, 0)) {
+					case -EAGAIN:
+						set_page_attr(bitmap, page, BITMAP_PAGE_NEEDWRITE);
+						break;
+					case 0:
+						break;
+					default:
+						bitmap_file_kick(bitmap);
+					}
+					page_cache_release(page);
+				}
+				continue;
+			}
+
+			/* grab the new page, sync and release the old */
+			page_cache_get(page);
+			if (lastpage != NULL) {
+				if (get_page_attr(bitmap, lastpage) & BITMAP_PAGE_NEEDWRITE) {
+					clear_page_attr(bitmap, lastpage, BITMAP_PAGE_NEEDWRITE);
+					spin_unlock_irqrestore(&bitmap->lock, flags);
+					err = write_page(bitmap, lastpage, 0);
+					if (err == -EAGAIN) {
+						err = 0;
+						set_page_attr(bitmap, lastpage, BITMAP_PAGE_NEEDWRITE);
+					}
+				} else {
+					set_page_attr(bitmap, lastpage, BITMAP_PAGE_NEEDWRITE);
+					spin_unlock_irqrestore(&bitmap->lock, flags);
+				}
+				kunmap(lastpage);
+				page_cache_release(lastpage);
+				if (err)
+					bitmap_file_kick(bitmap);
+			} else
+				spin_unlock_irqrestore(&bitmap->lock, flags);
+			lastpage = page;
+			kmap(page);
+/*
+			printk("bitmap clean at page %lu\n", j);
+*/
+			spin_lock_irqsave(&bitmap->lock, flags);
+			clear_page_attr(bitmap, page, BITMAP_PAGE_CLEAN);
+		}
+		bmc = bitmap_get_counter(bitmap, j << CHUNK_BLOCK_SHIFT(bitmap),
+					&blocks, 0);
+		if (bmc) {
+/*
+  if (j < 100) printk("bitmap: j=%lu, *bmc = 0x%x\n", j, *bmc);
+*/
+			if (*bmc == 2) {
+				*bmc=1; /* maybe clear the bit next time */
+				set_page_attr(bitmap, page, BITMAP_PAGE_CLEAN);
+			} else if (*bmc == 1) {
+				/* we can clear the bit */
+				*bmc = 0;
+				bitmap_count_page(bitmap, j << CHUNK_BLOCK_SHIFT(bitmap),
+						  -1);
+
+				/* clear the bit */
+				clear_bit(file_page_offset(j), page_address(page));
+			}
+		}
+		spin_unlock_irqrestore(&bitmap->lock, flags);
+	}
+
+	/* now sync the final page */
+	if (lastpage != NULL) {
+		kunmap(lastpage);
+		spin_lock_irqsave(&bitmap->lock, flags);
+		if (get_page_attr(bitmap, lastpage) &BITMAP_PAGE_NEEDWRITE) {
+			clear_page_attr(bitmap, lastpage, BITMAP_PAGE_NEEDWRITE);
+			spin_unlock_irqrestore(&bitmap->lock, flags);
+			err = write_page(bitmap, lastpage, 0);
+			if (err == -EAGAIN) {
+				set_page_attr(bitmap, lastpage, BITMAP_PAGE_NEEDWRITE);
+				err = 0;
+			}
+		} else {
+			set_page_attr(bitmap, lastpage, BITMAP_PAGE_NEEDWRITE);
+			spin_unlock_irqrestore(&bitmap->lock, flags);
+		}
+
+		page_cache_release(lastpage);
+	}
+
+	return err;
+}
+
+static void daemon_exit(struct bitmap *bitmap, mdk_thread_t **daemon)
+{
+	mdk_thread_t *dmn;
+	unsigned long flags;
+
+	/* if no one is waiting on us, we'll free the md thread struct
+	 * and exit, otherwise we let the waiter clean things up */
+	spin_lock_irqsave(&bitmap->lock, flags);
+	if ((dmn = *daemon)) { /* no one is waiting, cleanup and exit */
+		*daemon = NULL;
+		spin_unlock_irqrestore(&bitmap->lock, flags);
+		kfree(dmn);
+		complete_and_exit(NULL, 0); /* do_exit not exported */
+	}
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+}
+
+static void bitmap_writeback_daemon(mddev_t *mddev)
+{
+	struct bitmap *bitmap = mddev->bitmap;
+	struct page *page;
+	struct page_list *item;
+	int err = 0;
+
+	if (signal_pending(current)) {
+		printk(KERN_INFO
+		       "%s: bitmap writeback daemon got signal, exiting...\n",
+		       bmname(bitmap));
+		err = -EINTR;
+		goto out;
+	}
+
+	PRINTK("%s: bitmap writeback daemon woke up...\n", bmname(bitmap));
+	/* wait on bitmap page writebacks */
+	while ((item = dequeue_page(bitmap))) {
+		page = item->page;
+		mempool_free(item, bitmap->write_pool);
+		PRINTK("wait on page writeback: %p\n", page);
+		wait_on_page_writeback(page);
+		PRINTK("finished page writeback: %p\n", page);
+
+		err = PageError(page);
+		page_cache_release(page);
+		if (err) {
+			printk(KERN_WARNING "%s: bitmap file writeback "
+			       "failed (page %lu): %d\n",
+			       bmname(bitmap), page->index, err);
+			bitmap_file_kick(bitmap);
+			goto out;
+		}
+	}
+ out:
+	wake_up(&bitmap->write_wait);
+	if (err) {
+		printk(KERN_INFO "%s: bitmap writeback daemon exiting (%d)\n",
+		       bmname(bitmap), err);
+		daemon_exit(bitmap, &bitmap->writeback_daemon);
+	}
+}
+
+static int bitmap_start_daemon(struct bitmap *bitmap, mdk_thread_t **ptr,
+				void (*func)(mddev_t *), char *name)
+{
+	mdk_thread_t *daemon;
+	unsigned long flags;
+	char namebuf[32];
+
+	spin_lock_irqsave(&bitmap->lock, flags);
+	*ptr = NULL;
+
+	if (!bitmap->file) /* no need for daemon if there's no backing file */
+		goto out_unlock;
+
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+
+#if INJECT_FATAL_FAULT_2
+	daemon = NULL;
+#else
+	sprintf(namebuf, "%%s_%s", name);
+	daemon = md_register_thread(func, bitmap->mddev, namebuf);
+#endif
+	if (!daemon) {
+		printk(KERN_ERR "%s: failed to start bitmap daemon\n",
+			bmname(bitmap));
+		return -ECHILD;
+	}
+
+	spin_lock_irqsave(&bitmap->lock, flags);
+	*ptr = daemon;
+
+	md_wakeup_thread(daemon); /* start it running */
+
+	PRINTK("%s: %s daemon (pid %d) started...\n",
+		bmname(bitmap), name, daemon->tsk->pid);
+out_unlock:
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+	return 0;
+}
+
+static int bitmap_start_daemons(struct bitmap *bitmap)
+{
+	int err = bitmap_start_daemon(bitmap, &bitmap->writeback_daemon,
+					bitmap_writeback_daemon, "bitmap_wb");
+	return err;
+}
+
+static void bitmap_stop_daemon(struct bitmap *bitmap, mdk_thread_t **ptr)
+{
+	mdk_thread_t *daemon;
+	unsigned long flags;
+
+	spin_lock_irqsave(&bitmap->lock, flags);
+	daemon = *ptr;
+	*ptr = NULL;
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+	if (daemon)
+		md_unregister_thread(daemon); /* destroy the thread */
+}
+
+static void bitmap_stop_daemons(struct bitmap *bitmap)
+{
+	/* the daemons can't stop themselves... they'll just exit instead... */
+	if (bitmap->writeback_daemon &&
+	    current->pid != bitmap->writeback_daemon->tsk->pid)
+		bitmap_stop_daemon(bitmap, &bitmap->writeback_daemon);
+}
+
+static bitmap_counter_t *bitmap_get_counter(struct bitmap *bitmap,
+					    sector_t offset, int *blocks,
+					    int create)
+{
+	/* If 'create', we might release the lock and reclaim it.
+	 * The lock must have been taken with interrupts enabled.
+	 * If !create, we don't release the lock.
+	 */
+	sector_t chunk = offset >> CHUNK_BLOCK_SHIFT(bitmap);
+	unsigned long page = chunk >> PAGE_COUNTER_SHIFT;
+	unsigned long pageoff = (chunk & PAGE_COUNTER_MASK) << COUNTER_BYTE_SHIFT;
+	sector_t csize;
+
+	if (bitmap_checkpage(bitmap, page, create) < 0) {
+		csize = ((sector_t)1) << (CHUNK_BLOCK_SHIFT(bitmap));
+		*blocks = csize - (offset & (csize- 1));
+		return NULL;
+	}
+	/* now locked ... */
+
+	if (bitmap->bp[page].hijacked) { /* hijacked pointer */
+		/* should we use the first or second counter field
+		 * of the hijacked pointer? */
+		int hi = (pageoff > PAGE_COUNTER_MASK);
+		csize = ((sector_t)1) << (CHUNK_BLOCK_SHIFT(bitmap) +
+					  PAGE_COUNTER_SHIFT - 1);
+		*blocks = csize - (offset & (csize- 1));
+		return  &((bitmap_counter_t *)
+			  &bitmap->bp[page].map)[hi];
+	} else { /* page is allocated */
+		csize = ((sector_t)1) << (CHUNK_BLOCK_SHIFT(bitmap));
+		*blocks = csize - (offset & (csize- 1));
+		return (bitmap_counter_t *)
+			&(bitmap->bp[page].map[pageoff]);
+	}
+}
+
+int bitmap_startwrite(struct bitmap *bitmap, sector_t offset, unsigned long sectors)
+{
+	if (!bitmap) return 0;
+	while (sectors) {
+		int blocks;
+		bitmap_counter_t *bmc;
+
+		spin_lock_irq(&bitmap->lock);
+		bmc = bitmap_get_counter(bitmap, offset, &blocks, 1);
+		if (!bmc) {
+			spin_unlock_irq(&bitmap->lock);
+			return 0;
+		}
+
+		switch(*bmc) {
+		case 0:
+			bitmap_file_set_bit(bitmap, offset);
+			bitmap_count_page(bitmap,offset, 1);
+			blk_plug_device(bitmap->mddev->queue);
+			/* fall through */
+		case 1:
+			*bmc = 2;
+		}
+		if ((*bmc & COUNTER_MAX) == COUNTER_MAX) BUG();
+		(*bmc)++;
+
+		spin_unlock_irq(&bitmap->lock);
+
+		offset += blocks;
+		if (sectors > blocks)
+			sectors -= blocks;
+		else sectors = 0;
+	}
+	return 0;
+}
+
+void bitmap_endwrite(struct bitmap *bitmap, sector_t offset, unsigned long sectors,
+		     int success)
+{
+	if (!bitmap) return;
+	while (sectors) {
+		int blocks;
+		unsigned long flags;
+		bitmap_counter_t *bmc;
+
+		spin_lock_irqsave(&bitmap->lock, flags);
+		bmc = bitmap_get_counter(bitmap, offset, &blocks, 0);
+		if (!bmc) {
+			spin_unlock_irqrestore(&bitmap->lock, flags);
+			return;
+		}
+
+		if (!success && ! (*bmc & NEEDED_MASK))
+			*bmc |= NEEDED_MASK;
+
+		(*bmc)--;
+		if (*bmc <= 2) {
+			set_page_attr(bitmap,
+				      filemap_get_page(bitmap, offset >> CHUNK_BLOCK_SHIFT(bitmap)),
+				      BITMAP_PAGE_CLEAN);
+		}
+		spin_unlock_irqrestore(&bitmap->lock, flags);
+		offset += blocks;
+		if (sectors > blocks)
+			sectors -= blocks;
+		else sectors = 0;
+	}
+}
+
+int bitmap_start_sync(struct bitmap *bitmap, sector_t offset, int *blocks)
+{
+	bitmap_counter_t *bmc;
+	int rv;
+	if (bitmap == NULL) {/* FIXME or bitmap set as 'failed' */
+		*blocks = 1024;
+		return 1; /* always resync if no bitmap */
+	}
+	spin_lock_irq(&bitmap->lock);
+	bmc = bitmap_get_counter(bitmap, offset, blocks, 0);
+	rv = 0;
+	if (bmc) {
+		/* locked */
+		if (RESYNC(*bmc))
+			rv = 1;
+		else if (NEEDED(*bmc)) {
+			rv = 1;
+			*bmc |= RESYNC_MASK;
+			*bmc &= ~NEEDED_MASK;
+		}
+	}
+	spin_unlock_irq(&bitmap->lock);
+	return rv;
+}
+
+void bitmap_end_sync(struct bitmap *bitmap, sector_t offset, int *blocks, int aborted)
+{
+	bitmap_counter_t *bmc;
+	unsigned long flags;
+/*
+	if (offset == 0) printk("bitmap_end_sync 0 (%d)\n", aborted);
+*/	if (bitmap == NULL) {
+		*blocks = 1024;
+		return;
+	}
+	spin_lock_irqsave(&bitmap->lock, flags);
+	bmc = bitmap_get_counter(bitmap, offset, blocks, 0);
+	if (bmc == NULL)
+		goto unlock;
+	/* locked */
+/*
+	if (offset == 0) printk("bitmap_end sync found 0x%x, blocks %d\n", *bmc, *blocks);
+*/
+	if (RESYNC(*bmc)) {
+		*bmc &= ~RESYNC_MASK;
+
+		if (!NEEDED(*bmc) && aborted)
+			*bmc |= NEEDED_MASK;
+		else {
+			if (*bmc <= 2) {
+				set_page_attr(bitmap,
+					      filemap_get_page(bitmap, offset >> CHUNK_BLOCK_SHIFT(bitmap)),
+					      BITMAP_PAGE_CLEAN);
+			}
+		}
+	}
+ unlock:
+	spin_unlock_irqrestore(&bitmap->lock, flags);
+}
+
+void bitmap_close_sync(struct bitmap *bitmap)
+{
+	/* Sync has finished, and any bitmap chunks that weren't synced
+	 * properly have been aborted.  It remains to us to clear the
+	 * RESYNC bit wherever it is still on
+	 */
+	sector_t sector = 0;
+	int blocks;
+	if (!bitmap) return;
+	while (sector < bitmap->mddev->resync_max_sectors) {
+		bitmap_end_sync(bitmap, sector, &blocks, 0);
+/*
+		if (sector < 500) printk("bitmap_close_sync: sec %llu blks %d\n",
+					 (unsigned long long)sector, blocks);
+*/		sector += blocks;
+	}
+}
+
+static void bitmap_set_memory_bits(struct bitmap *bitmap, sector_t offset,
+				   unsigned long sectors, int in_sync)
+{
+	/* For each chunk covered by any of these sectors, set the
+	 * counter to 1 and set resync_needed unless in_sync.  They should all
+	 * be 0 at this point
+	 */
+	while (sectors) {
+		int secs;
+		bitmap_counter_t *bmc;
+		spin_lock_irq(&bitmap->lock);
+		bmc = bitmap_get_counter(bitmap, offset, &secs, 1);
+		if (!bmc) {
+			spin_unlock_irq(&bitmap->lock);
+			return;
+		}
+		if (! *bmc) {
+			struct page *page;
+			*bmc = 1 | (in_sync? 0 : NEEDED_MASK);
+			bitmap_count_page(bitmap, offset, 1);
+			page = filemap_get_page(bitmap, offset >> CHUNK_BLOCK_SHIFT(bitmap));
+			set_page_attr(bitmap, page, BITMAP_PAGE_CLEAN);
+		}
+		spin_unlock_irq(&bitmap->lock);
+		if (sectors > secs)
+			sectors -= secs;
+		else
+			sectors = 0;
+	}
+}
+
+/*
+ * free memory that was allocated
+ */
+void bitmap_destroy(mddev_t *mddev)
+{
+	unsigned long k, pages;
+	struct bitmap_page *bp;
+	struct bitmap *bitmap = mddev->bitmap;
+
+	if (!bitmap) /* there was no bitmap */
+		return;
+
+	mddev->bitmap = NULL; /* disconnect from the md device */
+
+	/* release the bitmap file and kill the daemon */
+	bitmap_file_put(bitmap);
+
+	bp = bitmap->bp;
+	pages = bitmap->pages;
+
+	/* free all allocated memory */
+
+	mempool_destroy(bitmap->write_pool);
+
+	if (bp) /* deallocate the page memory */
+		for (k = 0; k < pages; k++)
+			if (bp[k].map && !bp[k].hijacked)
+				kfree(bp[k].map);
+	kfree(bp);
+	kfree(bitmap);
+}
+
+/*
+ * initialize the bitmap structure
+ * if this returns an error, bitmap_destroy must be called to do clean up
+ */
+int bitmap_create(mddev_t *mddev)
+{
+	struct bitmap *bitmap;
+	unsigned long blocks = mddev->resync_max_sectors;
+	unsigned long chunks;
+	unsigned long pages;
+	struct file *file = mddev->bitmap_file;
+	int err;
+
+	BUG_ON(sizeof(bitmap_super_t) != 256);
+
+	if (!file && !mddev->bitmap_offset) /* bitmap disabled, nothing to do */
+		return 0;
+
+	BUG_ON(file && mddev->bitmap_offset);
+
+	bitmap = kmalloc(sizeof(*bitmap), GFP_KERNEL);
+	if (!bitmap)
+		return -ENOMEM;
+
+	memset(bitmap, 0, sizeof(*bitmap));
+
+	spin_lock_init(&bitmap->lock);
+	bitmap->mddev = mddev;
+	mddev->bitmap = bitmap;
+
+	spin_lock_init(&bitmap->write_lock);
+	INIT_LIST_HEAD(&bitmap->complete_pages);
+	init_waitqueue_head(&bitmap->write_wait);
+	bitmap->write_pool = mempool_create(WRITE_POOL_SIZE, write_pool_alloc,
+				write_pool_free, NULL);
+	if (!bitmap->write_pool)
+		return -ENOMEM;
+
+	bitmap->file = file;
+	bitmap->offset = mddev->bitmap_offset;
+	if (file) get_file(file);
+	/* read superblock from bitmap file (this sets bitmap->chunksize) */
+	err = bitmap_read_sb(bitmap);
+	if (err)
+		return err;
+
+	bitmap->chunkshift = find_first_bit(&bitmap->chunksize,
+					sizeof(bitmap->chunksize));
+
+	/* now that chunksize and chunkshift are set, we can use these macros */
+ 	chunks = (blocks + CHUNK_BLOCK_RATIO(bitmap) - 1) /
+			CHUNK_BLOCK_RATIO(bitmap);
+ 	pages = (chunks + PAGE_COUNTER_RATIO - 1) / PAGE_COUNTER_RATIO;
+
+	BUG_ON(!pages);
+
+	bitmap->chunks = chunks;
+	bitmap->pages = pages;
+	bitmap->missing_pages = pages;
+	bitmap->counter_bits = COUNTER_BITS;
+
+	bitmap->syncchunk = ~0UL;
+
+#if INJECT_FATAL_FAULT_1
+	bitmap->bp = NULL;
+#else
+	bitmap->bp = kmalloc(pages * sizeof(*bitmap->bp), GFP_KERNEL);
+#endif
+	if (!bitmap->bp)
+		return -ENOMEM;
+	memset(bitmap->bp, 0, pages * sizeof(*bitmap->bp));
+
+	bitmap->flags |= BITMAP_ACTIVE;
+
+	/* now that we have some pages available, initialize the in-memory
+	 * bitmap from the on-disk bitmap */
+	err = bitmap_init_from_disk(bitmap, mddev->recovery_cp == MaxSector);
+	if (err)
+		return err;
+
+	printk(KERN_INFO "created bitmap (%lu pages) for device %s\n",
+		pages, bmname(bitmap));
+
+	/* kick off the bitmap daemons */
+	err = bitmap_start_daemons(bitmap);
+	if (err)
+		return err;
+	return bitmap_update_sb(bitmap);
+}
+
+/* the bitmap API -- for raid personalities */
+EXPORT_SYMBOL(bitmap_startwrite);
+EXPORT_SYMBOL(bitmap_endwrite);
+EXPORT_SYMBOL(bitmap_start_sync);
+EXPORT_SYMBOL(bitmap_end_sync);
+EXPORT_SYMBOL(bitmap_unplug);
+EXPORT_SYMBOL(bitmap_close_sync);
+EXPORT_SYMBOL(bitmap_daemon_work);
diff --git a/drivers/md/dm-crypt.c b/drivers/md/dm-crypt.c
index 0dd6c2b..d0a4bab 100644
--- a/drivers/md/dm-crypt.c
+++ b/drivers/md/dm-crypt.c
@@ -704,8 +704,7 @@
 	mempool_destroy(cc->page_pool);
 	mempool_destroy(cc->io_pool);
 
-	if (cc->iv_mode)
-		kfree(cc->iv_mode);
+	kfree(cc->iv_mode);
 	if (cc->iv_gen_ops && cc->iv_gen_ops->dtr)
 		cc->iv_gen_ops->dtr(cc);
 	crypto_free_tfm(cc->tfm);
diff --git a/drivers/md/linear.c b/drivers/md/linear.c
index b1941b8..8d74001 100644
--- a/drivers/md/linear.c
+++ b/drivers/md/linear.c
@@ -217,8 +217,7 @@
 	return 0;
 
 out:
-	if (conf)
-		kfree(conf);
+	kfree(conf);
 	return 1;
 }
 
diff --git a/drivers/md/md.c b/drivers/md/md.c
index d899204..0c6b5b6 100644
--- a/drivers/md/md.c
+++ b/drivers/md/md.c
@@ -19,6 +19,9 @@
 
      Neil Brown <neilb@cse.unsw.edu.au>.
 
+   - persistent bitmap code
+     Copyright (C) 2003-2004, Paul Clements, SteelEye Technology, Inc.
+
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2, or (at your option)
@@ -33,6 +36,7 @@
 #include <linux/config.h>
 #include <linux/linkage.h>
 #include <linux/raid/md.h>
+#include <linux/raid/bitmap.h>
 #include <linux/sysctl.h>
 #include <linux/devfs_fs_kernel.h>
 #include <linux/buffer_head.h> /* for invalidate_bdev */
@@ -40,6 +44,8 @@
 
 #include <linux/init.h>
 
+#include <linux/file.h>
+
 #ifdef CONFIG_KMOD
 #include <linux/kmod.h>
 #endif
@@ -189,8 +195,7 @@
 		if (mddev->unit == unit) {
 			mddev_get(mddev);
 			spin_unlock(&all_mddevs_lock);
-			if (new)
-				kfree(new);
+			kfree(new);
 			return mddev;
 		}
 
@@ -218,6 +223,8 @@
 	INIT_LIST_HEAD(&new->all_mddevs);
 	init_timer(&new->safemode_timer);
 	atomic_set(&new->active, 1);
+	spin_lock_init(&new->write_lock);
+	init_waitqueue_head(&new->sb_wait);
 
 	new->queue = blk_alloc_queue(GFP_KERNEL);
 	if (!new->queue) {
@@ -320,6 +327,40 @@
 }
 
 
+static int super_written(struct bio *bio, unsigned int bytes_done, int error)
+{
+	mdk_rdev_t *rdev = bio->bi_private;
+	if (bio->bi_size)
+		return 1;
+
+	if (error || !test_bit(BIO_UPTODATE, &bio->bi_flags))
+		md_error(rdev->mddev, rdev);
+
+	if (atomic_dec_and_test(&rdev->mddev->pending_writes))
+		wake_up(&rdev->mddev->sb_wait);
+	return 0;
+}
+
+void md_super_write(mddev_t *mddev, mdk_rdev_t *rdev,
+		   sector_t sector, int size, struct page *page)
+{
+	/* write first size bytes of page to sector of rdev
+	 * Increment mddev->pending_writes before returning
+	 * and decrement it on completion, waking up sb_wait
+	 * if zero is reached.
+	 * If an error occurred, call md_error
+	 */
+	struct bio *bio = bio_alloc(GFP_NOIO, 1);
+
+	bio->bi_bdev = rdev->bdev;
+	bio->bi_sector = sector;
+	bio_add_page(bio, page, size, 0);
+	bio->bi_private = rdev;
+	bio->bi_end_io = super_written;
+	atomic_inc(&mddev->pending_writes);
+	submit_bio((1<<BIO_RW)|(1<<BIO_RW_SYNC), bio);
+}
+
 static int bi_complete(struct bio *bio, unsigned int bytes_done, int error)
 {
 	if (bio->bi_size)
@@ -329,7 +370,7 @@
 	return 0;
 }
 
-static int sync_page_io(struct block_device *bdev, sector_t sector, int size,
+int sync_page_io(struct block_device *bdev, sector_t sector, int size,
 		   struct page *page, int rw)
 {
 	struct bio *bio = bio_alloc(GFP_NOIO, 1);
@@ -416,11 +457,8 @@
 		ret = 1;
 
 abort:
-	if (tmp1)
-		kfree(tmp1);
-	if (tmp2)
-		kfree(tmp2);
-
+	kfree(tmp1);
+	kfree(tmp2);
 	return ret;
 }
 
@@ -569,6 +607,8 @@
 	mdp_disk_t *desc;
 	mdp_super_t *sb = (mdp_super_t *)page_address(rdev->sb_page);
 
+	rdev->raid_disk = -1;
+	rdev->in_sync = 0;
 	if (mddev->raid_disks == 0) {
 		mddev->major_version = 0;
 		mddev->minor_version = sb->minor_version;
@@ -599,16 +639,35 @@
 		memcpy(mddev->uuid+12,&sb->set_uuid3, 4);
 
 		mddev->max_disks = MD_SB_DISKS;
-	} else {
-		__u64 ev1;
-		ev1 = md_event(sb);
+
+		if (sb->state & (1<<MD_SB_BITMAP_PRESENT) &&
+		    mddev->bitmap_file == NULL) {
+			if (mddev->level != 1) {
+				/* FIXME use a better test */
+				printk(KERN_WARNING "md: bitmaps only support for raid1\n");
+				return -EINVAL;
+			}
+			mddev->bitmap_offset = (MD_SB_BYTES >> 9);
+		}
+
+	} else if (mddev->pers == NULL) {
+		/* Insist on good event counter while assembling */
+		__u64 ev1 = md_event(sb);
 		++ev1;
 		if (ev1 < mddev->events) 
 			return -EINVAL;
-	}
+	} else if (mddev->bitmap) {
+		/* if adding to array with a bitmap, then we can accept an
+		 * older device ... but not too old.
+		 */
+		__u64 ev1 = md_event(sb);
+		if (ev1 < mddev->bitmap->events_cleared)
+			return 0;
+	} else /* just a hot-add of a new device, leave raid_disk at -1 */
+		return 0;
+
 	if (mddev->level != LEVEL_MULTIPATH) {
-		rdev->raid_disk = -1;
-		rdev->in_sync = rdev->faulty = 0;
+		rdev->faulty = 0;
 		desc = sb->disks + rdev->desc_nr;
 
 		if (desc->state & (1<<MD_DISK_FAULTY))
@@ -618,7 +677,8 @@
 			rdev->in_sync = 1;
 			rdev->raid_disk = desc->raid_disk;
 		}
-	}
+	} else /* MULTIPATH are always insync */
+		rdev->in_sync = 1;
 	return 0;
 }
 
@@ -683,6 +743,9 @@
 	sb->layout = mddev->layout;
 	sb->chunk_size = mddev->chunk_size;
 
+	if (mddev->bitmap && mddev->bitmap_file == NULL)
+		sb->state |= (1<<MD_SB_BITMAP_PRESENT);
+
 	sb->disks[0].state = (1<<MD_DISK_REMOVED);
 	ITERATE_RDEV(mddev,rdev2,tmp) {
 		mdp_disk_t *d;
@@ -780,7 +843,7 @@
 	case 0:
 		sb_offset = rdev->bdev->bd_inode->i_size >> 9;
 		sb_offset -= 8*2;
-		sb_offset &= ~(4*2-1);
+		sb_offset &= ~(sector_t)(4*2-1);
 		/* convert from sectors to K */
 		sb_offset /= 2;
 		break;
@@ -860,6 +923,8 @@
 {
 	struct mdp_superblock_1 *sb = (struct mdp_superblock_1*)page_address(rdev->sb_page);
 
+	rdev->raid_disk = -1;
+	rdev->in_sync = 0;
 	if (mddev->raid_disks == 0) {
 		mddev->major_version = 1;
 		mddev->patch_version = 0;
@@ -877,13 +942,30 @@
 		memcpy(mddev->uuid, sb->set_uuid, 16);
 
 		mddev->max_disks =  (4096-256)/2;
-	} else {
-		__u64 ev1;
-		ev1 = le64_to_cpu(sb->events);
+
+		if ((le32_to_cpu(sb->feature_map) & 1) &&
+		    mddev->bitmap_file == NULL ) {
+			if (mddev->level != 1) {
+				printk(KERN_WARNING "md: bitmaps only supported for raid1\n");
+				return -EINVAL;
+			}
+			mddev->bitmap_offset = (__s32)le32_to_cpu(sb->bitmap_offset);
+		}
+	} else if (mddev->pers == NULL) {
+		/* Insist of good event counter while assembling */
+		__u64 ev1 = le64_to_cpu(sb->events);
 		++ev1;
 		if (ev1 < mddev->events)
 			return -EINVAL;
-	}
+	} else if (mddev->bitmap) {
+		/* If adding to array with a bitmap, then we can accept an
+		 * older device, but not too old.
+		 */
+		__u64 ev1 = le64_to_cpu(sb->events);
+		if (ev1 < mddev->bitmap->events_cleared)
+			return 0;
+	} else /* just a hot-add of a new device, leave raid_disk at -1 */
+		return 0;
 
 	if (mddev->level != LEVEL_MULTIPATH) {
 		int role;
@@ -891,14 +973,10 @@
 		role = le16_to_cpu(sb->dev_roles[rdev->desc_nr]);
 		switch(role) {
 		case 0xffff: /* spare */
-			rdev->in_sync = 0;
 			rdev->faulty = 0;
-			rdev->raid_disk = -1;
 			break;
 		case 0xfffe: /* faulty */
-			rdev->in_sync = 0;
 			rdev->faulty = 1;
-			rdev->raid_disk = -1;
 			break;
 		default:
 			rdev->in_sync = 1;
@@ -906,7 +984,9 @@
 			rdev->raid_disk = role;
 			break;
 		}
-	}
+	} else /* MULTIPATH are always insync */
+		rdev->in_sync = 1;
+
 	return 0;
 }
 
@@ -933,6 +1013,11 @@
 	else
 		sb->resync_offset = cpu_to_le64(0);
 
+	if (mddev->bitmap && mddev->bitmap_file == NULL) {
+		sb->bitmap_offset = cpu_to_le32((__u32)mddev->bitmap_offset);
+		sb->feature_map = cpu_to_le32(1);
+	}
+
 	max_dev = 0;
 	ITERATE_RDEV(mddev,rdev2,tmp)
 		if (rdev2->desc_nr+1 > max_dev)
@@ -1196,8 +1281,11 @@
 	printk("md:	* <COMPLETE RAID STATE PRINTOUT> *\n");
 	printk("md:	**********************************\n");
 	ITERATE_MDDEV(mddev,tmp) {
-		printk("%s: ", mdname(mddev));
 
+		if (mddev->bitmap)
+			bitmap_print_sb(mddev->bitmap);
+		else
+			printk("%s: ", mdname(mddev));
 		ITERATE_RDEV(mddev,rdev,tmp2)
 			printk("<%s>", bdevname(rdev->bdev,b));
 		printk("\n");
@@ -1210,30 +1298,6 @@
 }
 
 
-static int write_disk_sb(mdk_rdev_t * rdev)
-{
-	char b[BDEVNAME_SIZE];
-	if (!rdev->sb_loaded) {
-		MD_BUG();
-		return 1;
-	}
-	if (rdev->faulty) {
-		MD_BUG();
-		return 1;
-	}
-
-	dprintk(KERN_INFO "(write) %s's sb offset: %llu\n",
-		bdevname(rdev->bdev,b),
-	       (unsigned long long)rdev->sb_offset);
-  
-	if (sync_page_io(rdev->bdev, rdev->sb_offset<<1, MD_SB_BYTES, rdev->sb_page, WRITE))
-		return 0;
-
-	printk("md: write_disk_sb failed for device %s\n", 
-		bdevname(rdev->bdev,b));
-	return 1;
-}
-
 static void sync_sbs(mddev_t * mddev)
 {
 	mdk_rdev_t *rdev;
@@ -1248,12 +1312,14 @@
 
 static void md_update_sb(mddev_t * mddev)
 {
-	int err, count = 100;
+	int err;
 	struct list_head *tmp;
 	mdk_rdev_t *rdev;
+	int sync_req;
 
-	mddev->sb_dirty = 0;
 repeat:
+	spin_lock(&mddev->write_lock);
+	sync_req = mddev->in_sync;
 	mddev->utime = get_seconds();
 	mddev->events ++;
 
@@ -1266,20 +1332,26 @@
 		MD_BUG();
 		mddev->events --;
 	}
+	mddev->sb_dirty = 2;
 	sync_sbs(mddev);
 
 	/*
 	 * do not write anything to disk if using
 	 * nonpersistent superblocks
 	 */
-	if (!mddev->persistent)
+	if (!mddev->persistent) {
+		mddev->sb_dirty = 0;
+		spin_unlock(&mddev->write_lock);
+		wake_up(&mddev->sb_wait);
 		return;
+	}
+	spin_unlock(&mddev->write_lock);
 
 	dprintk(KERN_INFO 
 		"md: updating %s RAID superblock on device (in sync %d)\n",
 		mdname(mddev),mddev->in_sync);
 
-	err = 0;
+	err = bitmap_update_sb(mddev->bitmap);
 	ITERATE_RDEV(mddev,rdev,tmp) {
 		char b[BDEVNAME_SIZE];
 		dprintk(KERN_INFO "md: ");
@@ -1288,22 +1360,32 @@
 
 		dprintk("%s ", bdevname(rdev->bdev,b));
 		if (!rdev->faulty) {
-			err += write_disk_sb(rdev);
+			md_super_write(mddev,rdev,
+				       rdev->sb_offset<<1, MD_SB_BYTES,
+				       rdev->sb_page);
+			dprintk(KERN_INFO "(write) %s's sb offset: %llu\n",
+				bdevname(rdev->bdev,b),
+				(unsigned long long)rdev->sb_offset);
+
 		} else
 			dprintk(")\n");
-		if (!err && mddev->level == LEVEL_MULTIPATH)
+		if (mddev->level == LEVEL_MULTIPATH)
 			/* only need to write one superblock... */
 			break;
 	}
-	if (err) {
-		if (--count) {
-			printk(KERN_ERR "md: errors occurred during superblock"
-				" update, repeating\n");
-			goto repeat;
-		}
-		printk(KERN_ERR \
-			"md: excessive errors occurred during superblock update, exiting\n");
+	wait_event(mddev->sb_wait, atomic_read(&mddev->pending_writes)==0);
+	/* if there was a failure, sb_dirty was set to 1, and we re-write super */
+
+	spin_lock(&mddev->write_lock);
+	if (mddev->in_sync != sync_req|| mddev->sb_dirty == 1) {
+		/* have to write it out again */
+		spin_unlock(&mddev->write_lock);
+		goto repeat;
 	}
+	mddev->sb_dirty = 0;
+	spin_unlock(&mddev->write_lock);
+	wake_up(&mddev->sb_wait);
+
 }
 
 /*
@@ -1607,12 +1689,19 @@
 
 	mddev->resync_max_sectors = mddev->size << 1; /* may be over-ridden by personality */
 
-	err = mddev->pers->run(mddev);
+	/* before we start the array running, initialise the bitmap */
+	err = bitmap_create(mddev);
+	if (err)
+		printk(KERN_ERR "%s: failed to create bitmap (%d)\n",
+			mdname(mddev), err);
+	else
+		err = mddev->pers->run(mddev);
 	if (err) {
 		printk(KERN_ERR "md: pers->run() failed ...\n");
 		module_put(mddev->pers->owner);
 		mddev->pers = NULL;
-		return -EINVAL;
+		bitmap_destroy(mddev);
+		return err;
 	}
  	atomic_set(&mddev->writes_pending,0);
 	mddev->safemode = 0;
@@ -1725,6 +1814,14 @@
 		if (ro)
 			set_disk_ro(disk, 1);
 	}
+
+	bitmap_destroy(mddev);
+	if (mddev->bitmap_file) {
+		atomic_set(&mddev->bitmap_file->f_dentry->d_inode->i_writecount, 1);
+		fput(mddev->bitmap_file);
+		mddev->bitmap_file = NULL;
+	}
+
 	/*
 	 * Free resources if final stop
 	 */
@@ -1983,6 +2080,42 @@
 	return 0;
 }
 
+static int get_bitmap_file(mddev_t * mddev, void * arg)
+{
+	mdu_bitmap_file_t *file = NULL; /* too big for stack allocation */
+	char *ptr, *buf = NULL;
+	int err = -ENOMEM;
+
+	file = kmalloc(sizeof(*file), GFP_KERNEL);
+	if (!file)
+		goto out;
+
+	/* bitmap disabled, zero the first byte and copy out */
+	if (!mddev->bitmap || !mddev->bitmap->file) {
+		file->pathname[0] = '\0';
+		goto copy_out;
+	}
+
+	buf = kmalloc(sizeof(file->pathname), GFP_KERNEL);
+	if (!buf)
+		goto out;
+
+	ptr = file_path(mddev->bitmap->file, buf, sizeof(file->pathname));
+	if (!ptr)
+		goto out;
+
+	strcpy(file->pathname, ptr);
+
+copy_out:
+	err = 0;
+	if (copy_to_user(arg, file, sizeof(*file)))
+		err = -EFAULT;
+out:
+	kfree(buf);
+	kfree(file);
+	return err;
+}
+
 static int get_disk_info(mddev_t * mddev, void __user * arg)
 {
 	mdu_disk_info_t info;
@@ -2078,11 +2211,25 @@
 				PTR_ERR(rdev));
 			return PTR_ERR(rdev);
 		}
+		/* set save_raid_disk if appropriate */
+		if (!mddev->persistent) {
+			if (info->state & (1<<MD_DISK_SYNC)  &&
+			    info->raid_disk < mddev->raid_disks)
+				rdev->raid_disk = info->raid_disk;
+			else
+				rdev->raid_disk = -1;
+		} else
+			super_types[mddev->major_version].
+				validate_super(mddev, rdev);
+		rdev->saved_raid_disk = rdev->raid_disk;
+
 		rdev->in_sync = 0; /* just to be sure */
 		rdev->raid_disk = -1;
 		err = bind_rdev_to_array(rdev, mddev);
 		if (err)
 			export_rdev(rdev);
+
+		set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
 		if (mddev->thread)
 			md_wakeup_thread(mddev->thread);
 		return err;
@@ -2256,6 +2403,49 @@
 	return err;
 }
 
+/* similar to deny_write_access, but accounts for our holding a reference
+ * to the file ourselves */
+static int deny_bitmap_write_access(struct file * file)
+{
+	struct inode *inode = file->f_mapping->host;
+
+	spin_lock(&inode->i_lock);
+	if (atomic_read(&inode->i_writecount) > 1) {
+		spin_unlock(&inode->i_lock);
+		return -ETXTBSY;
+	}
+	atomic_set(&inode->i_writecount, -1);
+	spin_unlock(&inode->i_lock);
+
+	return 0;
+}
+
+static int set_bitmap_file(mddev_t *mddev, int fd)
+{
+	int err;
+
+	if (mddev->pers)
+		return -EBUSY;
+
+	mddev->bitmap_file = fget(fd);
+
+	if (mddev->bitmap_file == NULL) {
+		printk(KERN_ERR "%s: error: failed to get bitmap file\n",
+			mdname(mddev));
+		return -EBADF;
+	}
+
+	err = deny_bitmap_write_access(mddev->bitmap_file);
+	if (err) {
+		printk(KERN_ERR "%s: error: bitmap file is already in use\n",
+			mdname(mddev));
+		fput(mddev->bitmap_file);
+		mddev->bitmap_file = NULL;
+	} else
+		mddev->bitmap_offset = 0; /* file overrides offset */
+	return err;
+}
+
 /*
  * set_array_info is used two different ways
  * The original usage is when creating a new array.
@@ -2567,8 +2757,10 @@
 	/*
 	 * Commands querying/configuring an existing array:
 	 */
-	/* if we are initialised yet, only ADD_NEW_DISK or STOP_ARRAY is allowed */
-	if (!mddev->raid_disks && cmd != ADD_NEW_DISK && cmd != STOP_ARRAY && cmd != RUN_ARRAY) {
+	/* if we are not initialised yet, only ADD_NEW_DISK, STOP_ARRAY,
+	 * RUN_ARRAY, and SET_BITMAP_FILE are allowed */
+	if (!mddev->raid_disks && cmd != ADD_NEW_DISK && cmd != STOP_ARRAY
+			&& cmd != RUN_ARRAY && cmd != SET_BITMAP_FILE) {
 		err = -ENODEV;
 		goto abort_unlock;
 	}
@@ -2582,6 +2774,10 @@
 			err = get_array_info(mddev, argp);
 			goto done_unlock;
 
+		case GET_BITMAP_FILE:
+			err = get_bitmap_file(mddev, (void *)arg);
+			goto done_unlock;
+
 		case GET_DISK_INFO:
 			err = get_disk_info(mddev, argp);
 			goto done_unlock;
@@ -2662,6 +2858,10 @@
 			err = do_md_run (mddev);
 			goto done_unlock;
 
+		case SET_BITMAP_FILE:
+			err = set_bitmap_file(mddev, (int)arg);
+			goto done_unlock;
+
 		default:
 			if (_IOC_TYPE(cmd) == MD_MAJOR)
 				printk(KERN_WARNING "md: %s(pid %d) used"
@@ -2773,8 +2973,9 @@
 	while (thread->run) {
 		void (*run)(mddev_t *);
 
-		wait_event_interruptible(thread->wqueue,
-					 test_bit(THREAD_WAKEUP, &thread->flags));
+		wait_event_interruptible_timeout(thread->wqueue,
+						 test_bit(THREAD_WAKEUP, &thread->flags),
+						 thread->timeout);
 		if (current->flags & PF_FREEZE)
 			refrigerator(PF_FREEZE);
 
@@ -2820,6 +3021,7 @@
 	thread->run = run;
 	thread->mddev = mddev;
 	thread->name = name;
+	thread->timeout = MAX_SCHEDULE_TIMEOUT;
 	ret = kernel_thread(md_thread, thread, 0);
 	if (ret < 0) {
 		kfree(thread);
@@ -2858,13 +3060,13 @@
 
 	if (!rdev || rdev->faulty)
 		return;
-
+/*
 	dprintk("md_error dev:%s, rdev:(%d:%d), (caller: %p,%p,%p,%p).\n",
 		mdname(mddev),
 		MAJOR(rdev->bdev->bd_dev), MINOR(rdev->bdev->bd_dev),
 		__builtin_return_address(0),__builtin_return_address(1),
 		__builtin_return_address(2),__builtin_return_address(3));
-
+*/
 	if (!mddev->pers->error_handler)
 		return;
 	mddev->pers->error_handler(mddev,rdev);
@@ -3018,6 +3220,7 @@
 	struct list_head *tmp2;
 	mdk_rdev_t *rdev;
 	int i;
+	struct bitmap *bitmap;
 
 	if (v == (void*)1) {
 		seq_printf(seq, "Personalities : ");
@@ -3070,10 +3273,35 @@
 		if (mddev->pers) {
 			mddev->pers->status (seq, mddev);
 	 		seq_printf(seq, "\n      ");
-			if (mddev->curr_resync > 2)
+			if (mddev->curr_resync > 2) {
 				status_resync (seq, mddev);
-			else if (mddev->curr_resync == 1 || mddev->curr_resync == 2)
-				seq_printf(seq, "	resync=DELAYED");
+				seq_printf(seq, "\n      ");
+			} else if (mddev->curr_resync == 1 || mddev->curr_resync == 2)
+				seq_printf(seq, "	resync=DELAYED\n      ");
+		} else
+			seq_printf(seq, "\n       ");
+
+		if ((bitmap = mddev->bitmap)) {
+			unsigned long chunk_kb;
+			unsigned long flags;
+			spin_lock_irqsave(&bitmap->lock, flags);
+			chunk_kb = bitmap->chunksize >> 10;
+			seq_printf(seq, "bitmap: %lu/%lu pages [%luKB], "
+				"%lu%s chunk",
+				bitmap->pages - bitmap->missing_pages,
+				bitmap->pages,
+				(bitmap->pages - bitmap->missing_pages)
+					<< (PAGE_SHIFT - 10),
+				chunk_kb ? chunk_kb : bitmap->chunksize,
+				chunk_kb ? "KB" : "B");
+			if (bitmap->file) {
+				seq_printf(seq, ", file: ");
+				seq_path(seq, bitmap->file->f_vfsmnt,
+					 bitmap->file->f_dentry," \t\n");
+			}
+
+			seq_printf(seq, "\n");
+			spin_unlock_irqrestore(&bitmap->lock, flags);
 		}
 
 		seq_printf(seq, "\n");
@@ -3176,19 +3404,28 @@
 }
 
 
-void md_write_start(mddev_t *mddev)
+/* md_write_start(mddev, bi)
+ * If we need to update some array metadata (e.g. 'active' flag
+ * in superblock) before writing, schedule a superblock update
+ * and wait for it to complete.
+ */
+void md_write_start(mddev_t *mddev, struct bio *bi)
 {
-	if (!atomic_read(&mddev->writes_pending)) {
-		mddev_lock_uninterruptible(mddev);
+	DEFINE_WAIT(w);
+	if (bio_data_dir(bi) != WRITE)
+		return;
+
+	atomic_inc(&mddev->writes_pending);
+	if (mddev->in_sync) {
+		spin_lock(&mddev->write_lock);
 		if (mddev->in_sync) {
 			mddev->in_sync = 0;
- 			del_timer(&mddev->safemode_timer);
-			md_update_sb(mddev);
+			mddev->sb_dirty = 1;
+			md_wakeup_thread(mddev->thread);
 		}
-		atomic_inc(&mddev->writes_pending);
-		mddev_unlock(mddev);
-	} else
-		atomic_inc(&mddev->writes_pending);
+		spin_unlock(&mddev->write_lock);
+	}
+	wait_event(mddev->sb_wait, mddev->sb_dirty==0);
 }
 
 void md_write_end(mddev_t *mddev)
@@ -3201,37 +3438,6 @@
 	}
 }
 
-static inline void md_enter_safemode(mddev_t *mddev)
-{
-	if (!mddev->safemode) return;
-	if (mddev->safemode == 2 &&
-	    (atomic_read(&mddev->writes_pending) || mddev->in_sync ||
-		    mddev->recovery_cp != MaxSector))
-		return; /* avoid the lock */
-	mddev_lock_uninterruptible(mddev);
-	if (mddev->safemode && !atomic_read(&mddev->writes_pending) &&
-	    !mddev->in_sync && mddev->recovery_cp == MaxSector) {
-		mddev->in_sync = 1;
-		md_update_sb(mddev);
-	}
-	mddev_unlock(mddev);
-
-	if (mddev->safemode == 1)
-		mddev->safemode = 0;
-}
-
-void md_handle_safemode(mddev_t *mddev)
-{
-	if (signal_pending(current)) {
-		printk(KERN_INFO "md: %s in immediate safe mode\n",
-			mdname(mddev));
-		mddev->safemode = 2;
-		flush_signals(current);
-	}
-	md_enter_safemode(mddev);
-}
-
-
 static DECLARE_WAIT_QUEUE_HEAD(resync_wait);
 
 #define SYNC_MARKS	10
@@ -3241,12 +3447,13 @@
 	mddev_t *mddev2;
 	unsigned int currspeed = 0,
 		 window;
-	sector_t max_sectors,j;
+	sector_t max_sectors,j, io_sectors;
 	unsigned long mark[SYNC_MARKS];
 	sector_t mark_cnt[SYNC_MARKS];
 	int last_mark,m;
 	struct list_head *tmp;
 	sector_t last_check;
+	int skipped = 0;
 
 	/* just incase thread restarts... */
 	if (test_bit(MD_RECOVERY_DONE, &mddev->recovery))
@@ -3312,7 +3519,7 @@
 
 	if (test_bit(MD_RECOVERY_SYNC, &mddev->recovery))
 		/* resync follows the size requested by the personality,
-		 * which default to physical size, but can be virtual size
+		 * which defaults to physical size, but can be virtual size
 		 */
 		max_sectors = mddev->resync_max_sectors;
 	else
@@ -3327,13 +3534,15 @@
 	       sysctl_speed_limit_max);
 
 	is_mddev_idle(mddev); /* this also initializes IO event counters */
-	if (test_bit(MD_RECOVERY_SYNC, &mddev->recovery))
+	/* we don't use the checkpoint if there's a bitmap */
+	if (test_bit(MD_RECOVERY_SYNC, &mddev->recovery) && !mddev->bitmap)
 		j = mddev->recovery_cp;
 	else
 		j = 0;
+	io_sectors = 0;
 	for (m = 0; m < SYNC_MARKS; m++) {
 		mark[m] = jiffies;
-		mark_cnt[m] = j;
+		mark_cnt[m] = io_sectors;
 	}
 	last_mark = 0;
 	mddev->resync_mark = mark[last_mark];
@@ -3358,21 +3567,29 @@
 	}
 
 	while (j < max_sectors) {
-		int sectors;
+		sector_t sectors;
 
-		sectors = mddev->pers->sync_request(mddev, j, currspeed < sysctl_speed_limit_min);
-		if (sectors < 0) {
+		skipped = 0;
+		sectors = mddev->pers->sync_request(mddev, j, &skipped,
+					    currspeed < sysctl_speed_limit_min);
+		if (sectors == 0) {
 			set_bit(MD_RECOVERY_ERR, &mddev->recovery);
 			goto out;
 		}
-		atomic_add(sectors, &mddev->recovery_active);
+
+		if (!skipped) { /* actual IO requested */
+			io_sectors += sectors;
+			atomic_add(sectors, &mddev->recovery_active);
+		}
+
 		j += sectors;
 		if (j>1) mddev->curr_resync = j;
 
-		if (last_check + window > j || j == max_sectors)
+
+		if (last_check + window > io_sectors || j == max_sectors)
 			continue;
 
-		last_check = j;
+		last_check = io_sectors;
 
 		if (test_bit(MD_RECOVERY_INTR, &mddev->recovery) ||
 		    test_bit(MD_RECOVERY_ERR, &mddev->recovery))
@@ -3386,7 +3603,7 @@
 			mddev->resync_mark = mark[next];
 			mddev->resync_mark_cnt = mark_cnt[next];
 			mark[next] = jiffies;
-			mark_cnt[next] = j - atomic_read(&mddev->recovery_active);
+			mark_cnt[next] = io_sectors - atomic_read(&mddev->recovery_active);
 			last_mark = next;
 		}
 
@@ -3413,7 +3630,8 @@
 		mddev->queue->unplug_fn(mddev->queue);
 		cond_resched();
 
-		currspeed = ((unsigned long)(j-mddev->resync_mark_cnt))/2/((jiffies-mddev->resync_mark)/HZ +1) +1;
+		currspeed = ((unsigned long)(io_sectors-mddev->resync_mark_cnt))/2
+			/((jiffies-mddev->resync_mark)/HZ +1) +1;
 
 		if (currspeed > sysctl_speed_limit_min) {
 			if ((currspeed > sysctl_speed_limit_max) ||
@@ -3433,7 +3651,7 @@
 	wait_event(mddev->recovery_wait, !atomic_read(&mddev->recovery_active));
 
 	/* tell personality that we are finished */
-	mddev->pers->sync_request(mddev, max_sectors, 1);
+	mddev->pers->sync_request(mddev, max_sectors, &skipped, 1);
 
 	if (!test_bit(MD_RECOVERY_ERR, &mddev->recovery) &&
 	    mddev->curr_resync > 2 &&
@@ -3447,7 +3665,6 @@
 			mddev->recovery_cp = MaxSector;
 	}
 
-	md_enter_safemode(mddev);
  skip:
 	mddev->curr_resync = 0;
 	wake_up(&resync_wait);
@@ -3484,20 +3701,48 @@
 	struct list_head *rtmp;
 
 
-	dprintk(KERN_INFO "md: recovery thread got woken up ...\n");
+	if (mddev->bitmap)
+		bitmap_daemon_work(mddev->bitmap);
 
 	if (mddev->ro)
 		return;
+
+	if (signal_pending(current)) {
+		if (mddev->pers->sync_request) {
+			printk(KERN_INFO "md: %s in immediate safe mode\n",
+			       mdname(mddev));
+			mddev->safemode = 2;
+		}
+		flush_signals(current);
+	}
+
 	if ( ! (
 		mddev->sb_dirty ||
 		test_bit(MD_RECOVERY_NEEDED, &mddev->recovery) ||
-		test_bit(MD_RECOVERY_DONE, &mddev->recovery)
+		test_bit(MD_RECOVERY_DONE, &mddev->recovery) ||
+		(mddev->safemode == 1) ||
+		(mddev->safemode == 2 && ! atomic_read(&mddev->writes_pending)
+		 && !mddev->in_sync && mddev->recovery_cp == MaxSector)
 		))
 		return;
+
 	if (mddev_trylock(mddev)==0) {
 		int spares =0;
+
+		spin_lock(&mddev->write_lock);
+		if (mddev->safemode && !atomic_read(&mddev->writes_pending) &&
+		    !mddev->in_sync && mddev->recovery_cp == MaxSector) {
+			mddev->in_sync = 1;
+			mddev->sb_dirty = 1;
+		}
+		if (mddev->safemode == 1)
+			mddev->safemode = 0;
+		spin_unlock(&mddev->write_lock);
+
 		if (mddev->sb_dirty)
 			md_update_sb(mddev);
+
+
 		if (test_bit(MD_RECOVERY_RUNNING, &mddev->recovery) &&
 		    !test_bit(MD_RECOVERY_DONE, &mddev->recovery)) {
 			/* resync/recovery still happening */
@@ -3515,6 +3760,14 @@
 				mddev->pers->spare_active(mddev);
 			}
 			md_update_sb(mddev);
+
+			/* if array is no-longer degraded, then any saved_raid_disk
+			 * information must be scrapped
+			 */
+			if (!mddev->degraded)
+				ITERATE_RDEV(mddev,rdev,rtmp)
+					rdev->saved_raid_disk = -1;
+
 			mddev->recovery = 0;
 			/* flag recovery needed just to double check */
 			set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
@@ -3557,6 +3810,13 @@
 			set_bit(MD_RECOVERY_RUNNING, &mddev->recovery);
 			if (!spares)
 				set_bit(MD_RECOVERY_SYNC, &mddev->recovery);
+			if (spares && mddev->bitmap && ! mddev->bitmap->file) {
+				/* We are adding a device or devices to an array
+				 * which has the bitmap stored on all devices.
+				 * So make sure all bitmap pages get written
+				 */
+				bitmap_write_all(mddev->bitmap);
+			}
 			mddev->sync_thread = md_register_thread(md_do_sync,
 								mddev,
 								"%s_resync");
@@ -3624,6 +3884,8 @@
 			" MD_SB_DISKS=%d\n",
 			MD_MAJOR_VERSION, MD_MINOR_VERSION,
 			MD_PATCHLEVEL_VERSION, MAX_MD_DEVS, MD_SB_DISKS);
+	printk(KERN_INFO "md: bitmap version %d.%d\n", BITMAP_MAJOR,
+			BITMAP_MINOR);
 
 	if (register_blkdev(MAJOR_NR, "md"))
 		return -1;
@@ -3739,7 +4001,6 @@
 EXPORT_SYMBOL(md_done_sync);
 EXPORT_SYMBOL(md_write_start);
 EXPORT_SYMBOL(md_write_end);
-EXPORT_SYMBOL(md_handle_safemode);
 EXPORT_SYMBOL(md_register_thread);
 EXPORT_SYMBOL(md_unregister_thread);
 EXPORT_SYMBOL(md_wakeup_thread);
diff --git a/drivers/md/multipath.c b/drivers/md/multipath.c
index 2ae2d70..2d2ca7f 100644
--- a/drivers/md/multipath.c
+++ b/drivers/md/multipath.c
@@ -533,8 +533,7 @@
 out_free_conf:
 	if (conf->pool)
 		mempool_destroy(conf->pool);
-	if (conf->multipaths)
-		kfree(conf->multipaths);
+	kfree(conf->multipaths);
 	kfree(conf);
 	mddev->private = NULL;
 out:
diff --git a/drivers/md/raid0.c b/drivers/md/raid0.c
index e7d934e..e11dd14 100644
--- a/drivers/md/raid0.c
+++ b/drivers/md/raid0.c
@@ -371,10 +371,8 @@
 	return 0;
 
 out_free_conf:
-	if (conf->strip_zone)
-		kfree(conf->strip_zone);
-	if (conf->devlist)
-		kfree (conf->devlist);
+	kfree(conf->strip_zone);
+	kfree(conf->devlist);
 	kfree(conf);
 	mddev->private = NULL;
 out:
@@ -386,11 +384,11 @@
 	raid0_conf_t *conf = mddev_to_conf(mddev);
 
 	blk_sync_queue(mddev->queue); /* the unplug fn references 'conf'*/
-	kfree (conf->hash_table);
+	kfree(conf->hash_table);
 	conf->hash_table = NULL;
-	kfree (conf->strip_zone);
+	kfree(conf->strip_zone);
 	conf->strip_zone = NULL;
-	kfree (conf);
+	kfree(conf);
 	mddev->private = NULL;
 
 	return 0;
diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c
index 1db5de5..ff1dbec 100644
--- a/drivers/md/raid1.c
+++ b/drivers/md/raid1.c
@@ -12,6 +12,15 @@
  * Fixes to reconstruction by Jakob Østergaard" <jakob@ostenfeld.dk>
  * Various fixes by Neil Brown <neilb@cse.unsw.edu.au>
  *
+ * Changes by Peter T. Breuer <ptb@it.uc3m.es> 31/1/2003 to support
+ * bitmapped intelligence in resync:
+ *
+ *      - bitmap marked during normal i/o
+ *      - bitmap used to skip nondirty blocks during sync
+ *
+ * Additions to bitmap code, (C) 2003-2004 Paul Clements, SteelEye Technology:
+ * - persistent bitmap code
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2, or (at your option)
@@ -22,7 +31,16 @@
  * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  */
 
+#include "dm-bio-list.h"
 #include <linux/raid/raid1.h>
+#include <linux/raid/bitmap.h>
+
+#define DEBUG 0
+#if DEBUG
+#define PRINTK(x...) printk(x)
+#else
+#define PRINTK(x...)
+#endif
 
 /*
  * Number of guaranteed r1bios in case of extreme VM load:
@@ -287,9 +305,11 @@
 	/*
 	 * this branch is our 'one mirror IO has finished' event handler:
 	 */
-	if (!uptodate)
+	if (!uptodate) {
 		md_error(r1_bio->mddev, conf->mirrors[mirror].rdev);
-	else
+		/* an I/O failed, we can't clear the bitmap */
+		set_bit(R1BIO_Degraded, &r1_bio->state);
+	} else
 		/*
 		 * Set R1BIO_Uptodate in our master bio, so that
 		 * we will return a good error code for to the higher
@@ -309,6 +329,10 @@
 	 * already.
 	 */
 	if (atomic_dec_and_test(&r1_bio->remaining)) {
+		/* clear the bitmap if all writes complete successfully */
+		bitmap_endwrite(r1_bio->mddev->bitmap, r1_bio->sector,
+				r1_bio->sectors,
+				!test_bit(R1BIO_Degraded, &r1_bio->state));
 		md_write_end(r1_bio->mddev);
 		raid_end_bio_io(r1_bio);
 	}
@@ -458,7 +482,10 @@
 
 static void raid1_unplug(request_queue_t *q)
 {
-	unplug_slaves(q->queuedata);
+	mddev_t *mddev = q->queuedata;
+
+	unplug_slaves(mddev);
+	md_wakeup_thread(mddev->thread);
 }
 
 static int raid1_issue_flush(request_queue_t *q, struct gendisk *disk,
@@ -501,16 +528,16 @@
 {
 	spin_lock_irq(&conf->resync_lock);
 	wait_event_lock_irq(conf->wait_idle, !waitqueue_active(&conf->wait_resume),
-			    conf->resync_lock, unplug_slaves(conf->mddev));
+			    conf->resync_lock, raid1_unplug(conf->mddev->queue));
 	
 	if (!conf->barrier++) {
 		wait_event_lock_irq(conf->wait_idle, !conf->nr_pending,
-				    conf->resync_lock, unplug_slaves(conf->mddev));
+				    conf->resync_lock, raid1_unplug(conf->mddev->queue));
 		if (conf->nr_pending)
 			BUG();
 	}
 	wait_event_lock_irq(conf->wait_resume, conf->barrier < RESYNC_DEPTH,
-			    conf->resync_lock, unplug_slaves(conf->mddev));
+			    conf->resync_lock, raid1_unplug(conf->mddev->queue));
 	conf->next_resync = sect;
 	spin_unlock_irq(&conf->resync_lock);
 }
@@ -522,14 +549,20 @@
 	mirror_info_t *mirror;
 	r1bio_t *r1_bio;
 	struct bio *read_bio;
-	int i, disks;
+	int i, targets = 0, disks;
 	mdk_rdev_t *rdev;
+	struct bitmap *bitmap = mddev->bitmap;
+	unsigned long flags;
+	struct bio_list bl;
+
 
 	/*
 	 * Register the new request and wait if the reconstruction
 	 * thread has put up a bar for new requests.
 	 * Continue immediately if no resync is active currently.
 	 */
+	md_write_start(mddev, bio); /* wait on superblock update early */
+
 	spin_lock_irq(&conf->resync_lock);
 	wait_event_lock_irq(conf->wait_resume, !conf->barrier, conf->resync_lock, );
 	conf->nr_pending++;
@@ -552,7 +585,7 @@
 
 	r1_bio->master_bio = bio;
 	r1_bio->sectors = bio->bi_size >> 9;
-
+	r1_bio->state = 0;
 	r1_bio->mddev = mddev;
 	r1_bio->sector = bio->bi_sector;
 
@@ -595,6 +628,13 @@
 	 * bios[x] to bio
 	 */
 	disks = conf->raid_disks;
+#if 0
+	{ static int first=1;
+	if (first) printk("First Write sector %llu disks %d\n",
+			  (unsigned long long)r1_bio->sector, disks);
+	first = 0;
+	}
+#endif
 	rcu_read_lock();
 	for (i = 0;  i < disks; i++) {
 		if ((rdev=conf->mirrors[i].rdev) != NULL &&
@@ -605,13 +645,21 @@
 				r1_bio->bios[i] = NULL;
 			} else
 				r1_bio->bios[i] = bio;
+			targets++;
 		} else
 			r1_bio->bios[i] = NULL;
 	}
 	rcu_read_unlock();
 
-	atomic_set(&r1_bio->remaining, 1);
-	md_write_start(mddev);
+	if (targets < conf->raid_disks) {
+		/* array is degraded, we will not clear the bitmap
+		 * on I/O completion (see raid1_end_write_request) */
+		set_bit(R1BIO_Degraded, &r1_bio->state);
+	}
+
+	atomic_set(&r1_bio->remaining, 0);
+
+	bio_list_init(&bl);
 	for (i = 0; i < disks; i++) {
 		struct bio *mbio;
 		if (!r1_bio->bios[i])
@@ -627,13 +675,22 @@
 		mbio->bi_private = r1_bio;
 
 		atomic_inc(&r1_bio->remaining);
-		generic_make_request(mbio);
+
+		bio_list_add(&bl, mbio);
 	}
 
-	if (atomic_dec_and_test(&r1_bio->remaining)) {
-		md_write_end(mddev);
-		raid_end_bio_io(r1_bio);
-	}
+	bitmap_startwrite(bitmap, bio->bi_sector, r1_bio->sectors);
+	spin_lock_irqsave(&conf->device_lock, flags);
+	bio_list_merge(&conf->pending_bio_list, &bl);
+	bio_list_init(&bl);
+
+	blk_plug_device(mddev->queue);
+	spin_unlock_irqrestore(&conf->device_lock, flags);
+
+#if 0
+	while ((bio = bio_list_pop(&bl)) != NULL)
+		generic_make_request(bio);
+#endif
 
 	return 0;
 }
@@ -714,7 +771,7 @@
 {
 	spin_lock_irq(&conf->resync_lock);
 	wait_event_lock_irq(conf->wait_resume, !conf->barrier,
-			    conf->resync_lock, 	unplug_slaves(conf->mddev));
+			    conf->resync_lock, 	raid1_unplug(conf->mddev->queue));
 	spin_unlock_irq(&conf->resync_lock);
 
 	if (conf->barrier) BUG();
@@ -754,9 +811,12 @@
 {
 	conf_t *conf = mddev->private;
 	int found = 0;
-	int mirror;
+	int mirror = 0;
 	mirror_info_t *p;
 
+	if (rdev->saved_raid_disk >= 0 &&
+	    conf->mirrors[rdev->saved_raid_disk].rdev == NULL)
+		mirror = rdev->saved_raid_disk;
 	for (mirror=0; mirror < mddev->raid_disks; mirror++)
 		if ( !(p=conf->mirrors+mirror)->rdev) {
 
@@ -773,6 +833,8 @@
 			p->head_position = 0;
 			rdev->raid_disk = mirror;
 			found = 1;
+			if (rdev->saved_raid_disk != mirror)
+				conf->fullsync = 1;
 			p->rdev = rdev;
 			break;
 		}
@@ -828,10 +890,11 @@
 	 * or re-read if the read failed.
 	 * We don't do much here, just schedule handling by raid1d
 	 */
-	if (!uptodate)
+	if (!uptodate) {
 		md_error(r1_bio->mddev,
 			 conf->mirrors[r1_bio->read_disk].rdev);
-	else
+		set_bit(R1BIO_Degraded, &r1_bio->state);
+	} else
 		set_bit(R1BIO_Uptodate, &r1_bio->state);
 	rdev_dec_pending(conf->mirrors[r1_bio->read_disk].rdev, conf->mddev);
 	reschedule_retry(r1_bio);
@@ -855,8 +918,10 @@
 			mirror = i;
 			break;
 		}
-	if (!uptodate)
+	if (!uptodate) {
 		md_error(mddev, conf->mirrors[mirror].rdev);
+		set_bit(R1BIO_Degraded, &r1_bio->state);
+	}
 	update_head_pos(mirror, r1_bio);
 
 	if (atomic_dec_and_test(&r1_bio->remaining)) {
@@ -876,6 +941,9 @@
 
 	bio = r1_bio->bios[r1_bio->read_disk];
 
+/*
+	if (r1_bio->sector == 0) printk("First sync write startss\n");
+*/
 	/*
 	 * schedule writes
 	 */
@@ -903,10 +971,12 @@
 		atomic_inc(&conf->mirrors[i].rdev->nr_pending);
 		atomic_inc(&r1_bio->remaining);
 		md_sync_acct(conf->mirrors[i].rdev->bdev, wbio->bi_size >> 9);
+
 		generic_make_request(wbio);
 	}
 
 	if (atomic_dec_and_test(&r1_bio->remaining)) {
+		/* if we're here, all write(s) have completed, so clean up */
 		md_done_sync(mddev, r1_bio->sectors, 1);
 		put_buf(r1_bio);
 	}
@@ -931,11 +1001,30 @@
 	mdk_rdev_t *rdev;
 
 	md_check_recovery(mddev);
-	md_handle_safemode(mddev);
 	
 	for (;;) {
 		char b[BDEVNAME_SIZE];
 		spin_lock_irqsave(&conf->device_lock, flags);
+
+		if (conf->pending_bio_list.head) {
+			bio = bio_list_get(&conf->pending_bio_list);
+			blk_remove_plug(mddev->queue);
+			spin_unlock_irqrestore(&conf->device_lock, flags);
+			/* flush any pending bitmap writes to disk before proceeding w/ I/O */
+			if (bitmap_unplug(mddev->bitmap) != 0)
+				printk("%s: bitmap file write failed!\n", mdname(mddev));
+
+			while (bio) { /* submit pending writes */
+				struct bio *next = bio->bi_next;
+				bio->bi_next = NULL;
+				generic_make_request(bio);
+				bio = next;
+			}
+			unplug = 1;
+
+			continue;
+		}
+
 		if (list_empty(head))
 			break;
 		r1_bio = list_entry(head->prev, r1bio_t, retry_list);
@@ -1009,7 +1098,7 @@
  * that can be installed to exclude normal IO requests.
  */
 
-static int sync_request(mddev_t *mddev, sector_t sector_nr, int go_faster)
+static sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *skipped, int go_faster)
 {
 	conf_t *conf = mddev_to_conf(mddev);
 	mirror_info_t *mirror;
@@ -1019,17 +1108,43 @@
 	int disk;
 	int i;
 	int write_targets = 0;
+	int sync_blocks;
 
 	if (!conf->r1buf_pool)
+	{
+/*
+		printk("sync start - bitmap %p\n", mddev->bitmap);
+*/
 		if (init_resync(conf))
-			return -ENOMEM;
+			return 0;
+	}
 
 	max_sector = mddev->size << 1;
 	if (sector_nr >= max_sector) {
+		/* If we aborted, we need to abort the
+		 * sync on the 'current' bitmap chunk (there will
+		 * only be one in raid1 resync.
+		 * We can find the current addess in mddev->curr_resync
+		 */
+		if (!conf->fullsync) {
+			if (mddev->curr_resync < max_sector)
+				bitmap_end_sync(mddev->bitmap,
+						mddev->curr_resync,
+						&sync_blocks, 1);
+			bitmap_close_sync(mddev->bitmap);
+		}
+		if (mddev->curr_resync >= max_sector)
+			conf->fullsync = 0;
 		close_sync(conf);
 		return 0;
 	}
 
+	if (!conf->fullsync &&
+	    !bitmap_start_sync(mddev->bitmap, sector_nr, &sync_blocks)) {
+		/* We can skip this block, and probably several more */
+		*skipped = 1;
+		return sync_blocks;
+	}
 	/*
 	 * If there is non-resync activity waiting for us then
 	 * put in a delay to throttle resync.
@@ -1068,6 +1183,7 @@
 
 	r1_bio->mddev = mddev;
 	r1_bio->sector = sector_nr;
+	r1_bio->state = 0;
 	set_bit(R1BIO_IsSync, &r1_bio->state);
 	r1_bio->read_disk = disk;
 
@@ -1102,18 +1218,24 @@
 		bio->bi_bdev = conf->mirrors[i].rdev->bdev;
 		bio->bi_private = r1_bio;
 	}
+
+	if (write_targets + 1 < conf->raid_disks)
+		/* array degraded, can't clear bitmap */
+		set_bit(R1BIO_Degraded, &r1_bio->state);
+
 	if (write_targets == 0) {
 		/* There is nowhere to write, so all non-sync
 		 * drives must be failed - so we are finished
 		 */
-		int rv = max_sector - sector_nr;
-		md_done_sync(mddev, rv, 1);
+		sector_t rv = max_sector - sector_nr;
+		*skipped = 1;
 		put_buf(r1_bio);
 		rdev_dec_pending(conf->mirrors[disk].rdev, mddev);
 		return rv;
 	}
 
 	nr_sectors = 0;
+	sync_blocks = 0;
 	do {
 		struct page *page;
 		int len = PAGE_SIZE;
@@ -1121,6 +1243,17 @@
 			len = (max_sector - sector_nr) << 9;
 		if (len == 0)
 			break;
+		if (!conf->fullsync) {
+			if (sync_blocks == 0) {
+				if (!bitmap_start_sync(mddev->bitmap,
+						       sector_nr, &sync_blocks))
+					break;
+				if (sync_blocks < (PAGE_SIZE>>9))
+					BUG();
+				if (len > (sync_blocks<<9)) len = sync_blocks<<9;
+			}
+		}
+
 		for (i=0 ; i < conf->raid_disks; i++) {
 			bio = r1_bio->bios[i];
 			if (bio->bi_end_io) {
@@ -1143,6 +1276,7 @@
 		}
 		nr_sectors += len>>9;
 		sector_nr += len>>9;
+		sync_blocks -= (len>>9);
 	} while (r1_bio->bios[disk]->bi_vcnt < RESYNC_PAGES);
  bio_full:
 	bio = r1_bio->bios[disk];
@@ -1231,6 +1365,9 @@
 	init_waitqueue_head(&conf->wait_idle);
 	init_waitqueue_head(&conf->wait_resume);
 
+	bio_list_init(&conf->pending_bio_list);
+	bio_list_init(&conf->flushing_bio_list);
+
 	if (!conf->working_disks) {
 		printk(KERN_ERR "raid1: no operational mirrors for %s\n",
 			mdname(mddev));
@@ -1259,16 +1396,15 @@
 	conf->last_used = j;
 
 
-
-	{
-		mddev->thread = md_register_thread(raid1d, mddev, "%s_raid1");
-		if (!mddev->thread) {
-			printk(KERN_ERR 
-				"raid1: couldn't allocate thread for %s\n", 
-				mdname(mddev));
-			goto out_free_conf;
-		}
+	mddev->thread = md_register_thread(raid1d, mddev, "%s_raid1");
+	if (!mddev->thread) {
+		printk(KERN_ERR
+		       "raid1: couldn't allocate thread for %s\n",
+		       mdname(mddev));
+		goto out_free_conf;
 	}
+	if (mddev->bitmap) mddev->thread->timeout = mddev->bitmap->daemon_sleep * HZ;
+
 	printk(KERN_INFO 
 		"raid1: raid set %s active with %d out of %d mirrors\n",
 		mdname(mddev), mddev->raid_disks - mddev->degraded, 
@@ -1291,10 +1427,8 @@
 	if (conf) {
 		if (conf->r1bio_pool)
 			mempool_destroy(conf->r1bio_pool);
-		if (conf->mirrors)
-			kfree(conf->mirrors);
-		if (conf->poolinfo)
-			kfree(conf->poolinfo);
+		kfree(conf->mirrors);
+		kfree(conf->poolinfo);
 		kfree(conf);
 		mddev->private = NULL;
 	}
@@ -1311,10 +1445,8 @@
 	blk_sync_queue(mddev->queue); /* the unplug fn references 'conf'*/
 	if (conf->r1bio_pool)
 		mempool_destroy(conf->r1bio_pool);
-	if (conf->mirrors)
-		kfree(conf->mirrors);
-	if (conf->poolinfo)
-		kfree(conf->poolinfo);
+	kfree(conf->mirrors);
+	kfree(conf->poolinfo);
 	kfree(conf);
 	mddev->private = NULL;
 	return 0;
@@ -1349,17 +1481,26 @@
 	 * We allocate a new r1bio_pool if we can.
 	 * Then raise a device barrier and wait until all IO stops.
 	 * Then resize conf->mirrors and swap in the new r1bio pool.
+	 *
+	 * At the same time, we "pack" the devices so that all the missing
+	 * devices have the higher raid_disk numbers.
 	 */
 	mempool_t *newpool, *oldpool;
 	struct pool_info *newpoolinfo;
 	mirror_info_t *newmirrors;
 	conf_t *conf = mddev_to_conf(mddev);
+	int cnt;
 
-	int d;
+	int d, d2;
 
-	for (d= raid_disks; d < conf->raid_disks; d++)
-		if (conf->mirrors[d].rdev)
+	if (raid_disks < conf->raid_disks) {
+		cnt=0;
+		for (d= 0; d < conf->raid_disks; d++)
+			if (conf->mirrors[d].rdev)
+				cnt++;
+		if (cnt > raid_disks)
 			return -EBUSY;
+	}
 
 	newpoolinfo = kmalloc(sizeof(*newpoolinfo), GFP_KERNEL);
 	if (!newpoolinfo)
@@ -1384,14 +1525,18 @@
 	spin_lock_irq(&conf->resync_lock);
 	conf->barrier++;
 	wait_event_lock_irq(conf->wait_idle, !conf->nr_pending,
-			    conf->resync_lock, unplug_slaves(mddev));
+			    conf->resync_lock, raid1_unplug(mddev->queue));
 	spin_unlock_irq(&conf->resync_lock);
 
 	/* ok, everything is stopped */
 	oldpool = conf->r1bio_pool;
 	conf->r1bio_pool = newpool;
-	for (d=0; d < raid_disks && d < conf->raid_disks; d++)
-		newmirrors[d] = conf->mirrors[d];
+
+	for (d=d2=0; d < conf->raid_disks; d++)
+		if (conf->mirrors[d].rdev) {
+			conf->mirrors[d].rdev->raid_disk = d2;
+			newmirrors[d2++].rdev = conf->mirrors[d].rdev;
+		}
 	kfree(conf->mirrors);
 	conf->mirrors = newmirrors;
 	kfree(conf->poolinfo);
@@ -1400,6 +1545,7 @@
 	mddev->degraded += (raid_disks - conf->raid_disks);
 	conf->raid_disks = mddev->raid_disks = raid_disks;
 
+	conf->last_used = 0; /* just make sure it is in-range */
 	spin_lock_irq(&conf->resync_lock);
 	conf->barrier--;
 	spin_unlock_irq(&conf->resync_lock);
diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c
index 3c37be6..62ebb1b 100644
--- a/drivers/md/raid10.c
+++ b/drivers/md/raid10.c
@@ -700,6 +700,8 @@
 		return 0;
 	}
 
+	md_write_start(mddev, bio);
+
 	/*
 	 * Register the new request and wait if the reconstruction
 	 * thread has put up a bar for new requests.
@@ -774,7 +776,7 @@
 	rcu_read_unlock();
 
 	atomic_set(&r10_bio->remaining, 1);
-	md_write_start(mddev);
+
 	for (i = 0; i < conf->copies; i++) {
 		struct bio *mbio;
 		int d = r10_bio->devs[i].devnum;
@@ -1216,7 +1218,6 @@
 	mdk_rdev_t *rdev;
 
 	md_check_recovery(mddev);
-	md_handle_safemode(mddev);
 
 	for (;;) {
 		char b[BDEVNAME_SIZE];
@@ -1319,7 +1320,7 @@
  *
  */
 
-static int sync_request(mddev_t *mddev, sector_t sector_nr, int go_faster)
+static sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *skipped, int go_faster)
 {
 	conf_t *conf = mddev_to_conf(mddev);
 	r10bio_t *r10_bio;
@@ -1333,7 +1334,7 @@
 
 	if (!conf->r10buf_pool)
 		if (init_resync(conf))
-			return -ENOMEM;
+			return 0;
 
  skipped:
 	max_sector = mddev->size << 1;
@@ -1341,15 +1342,15 @@
 		max_sector = mddev->resync_max_sectors;
 	if (sector_nr >= max_sector) {
 		close_sync(conf);
+		*skipped = 1;
 		return sectors_skipped;
 	}
 	if (chunks_skipped >= conf->raid_disks) {
 		/* if there has been nothing to do on any drive,
 		 * then there is nothing to do at all..
 		 */
-		sector_t sec = max_sector - sector_nr;
-		md_done_sync(mddev, sec, 1);
-		return sec + sectors_skipped;
+		*skipped = 1;
+		return (max_sector - sector_nr) + sectors_skipped;
 	}
 
 	/* make sure whole request will fit in a chunk - if chunks
@@ -1563,17 +1564,22 @@
 		}
 	}
 
+	if (sectors_skipped)
+		/* pretend they weren't skipped, it makes
+		 * no important difference in this case
+		 */
+		md_done_sync(mddev, sectors_skipped, 1);
+
 	return sectors_skipped + nr_sectors;
  giveup:
 	/* There is nowhere to write, so all non-sync
 	 * drives must be failed, so try the next chunk...
 	 */
 	{
-	int sec = max_sector - sector_nr;
+	sector_t sec = max_sector - sector_nr;
 	sectors_skipped += sec;
 	chunks_skipped ++;
 	sector_nr = max_sector;
-	md_done_sync(mddev, sec, 1);
 	goto skipped;
 	}
 }
@@ -1731,8 +1737,7 @@
 out_free_conf:
 	if (conf->r10bio_pool)
 		mempool_destroy(conf->r10bio_pool);
-	if (conf->mirrors)
-		kfree(conf->mirrors);
+	kfree(conf->mirrors);
 	kfree(conf);
 	mddev->private = NULL;
 out:
@@ -1748,8 +1753,7 @@
 	blk_sync_queue(mddev->queue); /* the unplug fn references 'conf'*/
 	if (conf->r10bio_pool)
 		mempool_destroy(conf->r10bio_pool);
-	if (conf->mirrors)
-		kfree(conf->mirrors);
+	kfree(conf->mirrors);
 	kfree(conf);
 	mddev->private = NULL;
 	return 0;
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c
index 3cb11ac..93a9726 100644
--- a/drivers/md/raid5.c
+++ b/drivers/md/raid5.c
@@ -1411,6 +1411,8 @@
 	sector_t logical_sector, last_sector;
 	struct stripe_head *sh;
 
+	md_write_start(mddev, bi);
+
 	if (bio_data_dir(bi)==WRITE) {
 		disk_stat_inc(mddev->gendisk, writes);
 		disk_stat_add(mddev->gendisk, write_sectors, bio_sectors(bi));
@@ -1423,8 +1425,7 @@
 	last_sector = bi->bi_sector + (bi->bi_size>>9);
 	bi->bi_next = NULL;
 	bi->bi_phys_segments = 1;	/* over-loaded to count active stripes */
-	if ( bio_data_dir(bi) == WRITE )
-		md_write_start(mddev);
+
 	for (;logical_sector < last_sector; logical_sector += STRIPE_SECTORS) {
 		DEFINE_WAIT(w);
 		
@@ -1475,7 +1476,7 @@
 }
 
 /* FIXME go_faster isn't used */
-static int sync_request (mddev_t *mddev, sector_t sector_nr, int go_faster)
+static sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *skipped, int go_faster)
 {
 	raid5_conf_t *conf = (raid5_conf_t *) mddev->private;
 	struct stripe_head *sh;
@@ -1498,8 +1499,8 @@
 	 * nothing we can do.
 	 */
 	if (mddev->degraded >= 1 && test_bit(MD_RECOVERY_SYNC, &mddev->recovery)) {
-		int rv = (mddev->size << 1) - sector_nr;
-		md_done_sync(mddev, rv, 1);
+		sector_t rv = (mddev->size << 1) - sector_nr;
+		*skipped = 1;
 		return rv;
 	}
 
@@ -1546,7 +1547,6 @@
 	PRINTK("+++ raid5d active\n");
 
 	md_check_recovery(mddev);
-	md_handle_safemode(mddev);
 
 	handled = 0;
 	spin_lock_irq(&conf->device_lock);
diff --git a/drivers/md/raid6main.c b/drivers/md/raid6main.c
index 908edd7..f62ea1a 100644
--- a/drivers/md/raid6main.c
+++ b/drivers/md/raid6main.c
@@ -1570,6 +1570,8 @@
 	sector_t logical_sector, last_sector;
 	struct stripe_head *sh;
 
+	md_write_start(mddev, bi);
+
 	if (bio_data_dir(bi)==WRITE) {
 		disk_stat_inc(mddev->gendisk, writes);
 		disk_stat_add(mddev->gendisk, write_sectors, bio_sectors(bi));
@@ -1583,8 +1585,7 @@
 
 	bi->bi_next = NULL;
 	bi->bi_phys_segments = 1;	/* over-loaded to count active stripes */
-	if ( bio_data_dir(bi) == WRITE )
-		md_write_start(mddev);
+
 	for (;logical_sector < last_sector; logical_sector += STRIPE_SECTORS) {
 		DEFINE_WAIT(w);
 
@@ -1634,7 +1635,7 @@
 }
 
 /* FIXME go_faster isn't used */
-static int sync_request (mddev_t *mddev, sector_t sector_nr, int go_faster)
+static sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *skipped, int go_faster)
 {
 	raid6_conf_t *conf = (raid6_conf_t *) mddev->private;
 	struct stripe_head *sh;
@@ -1657,8 +1658,8 @@
 	 * nothing we can do.
 	 */
 	if (mddev->degraded >= 2 && test_bit(MD_RECOVERY_SYNC, &mddev->recovery)) {
-		int rv = (mddev->size << 1) - sector_nr;
-		md_done_sync(mddev, rv, 1);
+		sector_t rv = (mddev->size << 1) - sector_nr;
+		*skipped = 1;
 		return rv;
 	}
 
@@ -1705,7 +1706,6 @@
 	PRINTK("+++ raid6d active\n");
 
 	md_check_recovery(mddev);
-	md_handle_safemode(mddev);
 
 	handled = 0;
 	spin_lock_irq(&conf->device_lock);
diff --git a/drivers/misc/ibmasm/command.c b/drivers/misc/ibmasm/command.c
index 245b005..07a085c 100644
--- a/drivers/misc/ibmasm/command.c
+++ b/drivers/misc/ibmasm/command.c
@@ -23,6 +23,7 @@
  */
 
 #include "ibmasm.h"
+#include "lowlevel.h"
 
 static void exec_next_command(struct service_processor *sp);
 static void free_command(struct kobject *kobj);
@@ -31,8 +32,9 @@
 	.release = free_command,
 };
 
+static atomic_t command_count = ATOMIC_INIT(0);
 
-struct command *ibmasm_new_command(size_t buffer_size)
+struct command *ibmasm_new_command(struct service_processor *sp, size_t buffer_size)
 {
 	struct command *cmd;
 
@@ -55,11 +57,15 @@
 
 	kobject_init(&cmd->kobj);
 	cmd->kobj.ktype = &ibmasm_cmd_kobj_type;
+	cmd->lock = &sp->lock;
 
 	cmd->status = IBMASM_CMD_PENDING;
 	init_waitqueue_head(&cmd->wait);
 	INIT_LIST_HEAD(&cmd->queue_node);
 
+	atomic_inc(&command_count);
+	dbg("command count: %d\n", atomic_read(&command_count));
+
 	return cmd;
 }
 
@@ -68,6 +74,8 @@
 	struct command *cmd = to_command(kobj);
  
 	list_del(&cmd->queue_node);
+	atomic_dec(&command_count);
+	dbg("command count: %d\n", atomic_read(&command_count));
 	kfree(cmd->buffer);
 	kfree(cmd);
 }
@@ -94,8 +102,14 @@
 
 static inline void do_exec_command(struct service_processor *sp)
 {
+	char tsbuf[32];
+
+	dbg("%s:%d at %s\n", __FUNCTION__, __LINE__, get_timestamp(tsbuf));
+
 	if (ibmasm_send_i2o_message(sp)) {
 		sp->current_command->status = IBMASM_CMD_FAILED;
+		wake_up(&sp->current_command->wait);
+		command_put(sp->current_command);
 		exec_next_command(sp);
 	}
 }
@@ -111,14 +125,16 @@
 void ibmasm_exec_command(struct service_processor *sp, struct command *cmd)
 {
 	unsigned long flags;
+	char tsbuf[32];
+
+	dbg("%s:%d at %s\n", __FUNCTION__, __LINE__, get_timestamp(tsbuf));
 
 	spin_lock_irqsave(&sp->lock, flags);
 
 	if (!sp->current_command) {
-		command_get(cmd);
 		sp->current_command = cmd;
+		command_get(sp->current_command);
 		spin_unlock_irqrestore(&sp->lock, flags);
-
 		do_exec_command(sp);
 	} else {
 		enqueue_command(sp, cmd);
@@ -129,9 +145,9 @@
 static void exec_next_command(struct service_processor *sp)
 {
 	unsigned long flags;
+	char tsbuf[32];
 
-	wake_up(&sp->current_command->wait);
-	command_put(sp->current_command);
+	dbg("%s:%d at %s\n", __FUNCTION__, __LINE__, get_timestamp(tsbuf));
 
 	spin_lock_irqsave(&sp->lock, flags);
 	sp->current_command = dequeue_command(sp);
@@ -169,7 +185,9 @@
 	if (!sp->current_command) 
 		return; 
 
-	memcpy(cmd->buffer, response, min(size, cmd->buffer_size));
+	memcpy_fromio(cmd->buffer, response, min(size, cmd->buffer_size));
 	cmd->status = IBMASM_CMD_COMPLETE;
+	wake_up(&sp->current_command->wait);
+	command_put(sp->current_command);
 	exec_next_command(sp);
 }
diff --git a/drivers/misc/ibmasm/dot_command.c b/drivers/misc/ibmasm/dot_command.c
index 478a8d8..13c52f8 100644
--- a/drivers/misc/ibmasm/dot_command.c
+++ b/drivers/misc/ibmasm/dot_command.c
@@ -33,7 +33,13 @@
 	u32 size;
 	struct dot_command_header *header = (struct dot_command_header *)message;
 
+	if (message_size == 0)
+		return;
+
 	size = get_dot_command_size(message);
+	if (size == 0)
+		return;
+
 	if (size > message_size)
 		size = message_size;
 
@@ -67,7 +73,7 @@
 	u8 *vpd_data;
 	int result = 0;
 
-	command = ibmasm_new_command(INIT_BUFFER_SIZE);
+	command = ibmasm_new_command(sp, INIT_BUFFER_SIZE);
 	if (command == NULL)
 		return -ENOMEM;
 
@@ -121,7 +127,7 @@
 	struct os_state_command *os_state_cmd;
 	int result = 0;
 
-	cmd = ibmasm_new_command(sizeof(struct os_state_command));
+	cmd = ibmasm_new_command(sp, sizeof(struct os_state_command));
 	if (cmd == NULL)
 		return -ENOMEM;
 
diff --git a/drivers/misc/ibmasm/event.c b/drivers/misc/ibmasm/event.c
index e100f34..fe1e819 100644
--- a/drivers/misc/ibmasm/event.c
+++ b/drivers/misc/ibmasm/event.c
@@ -23,6 +23,7 @@
  */
 
 #include "ibmasm.h"
+#include "lowlevel.h"
 
 /*
  * ASM service processor event handling routines.
@@ -34,7 +35,6 @@
  * circular buffer.
  */
 
-
 static void wake_up_event_readers(struct service_processor *sp)
 {
 	struct event_reader *reader;
@@ -63,7 +63,7 @@
 	spin_lock_irqsave(&sp->lock, flags);
 	/* copy the event into the next slot in the circular buffer */
 	event = &buffer->events[buffer->next_index];
-	memcpy(event->data, data, data_size);
+	memcpy_fromio(event->data, data, data_size);
 	event->data_size = data_size;
 	event->serial_number = buffer->next_serial_number;
 
@@ -93,7 +93,10 @@
 	unsigned int index;
 	unsigned long flags;
 
-	if (wait_event_interruptible(reader->wait, event_available(buffer, reader)))
+	reader->cancelled = 0;
+
+	if (wait_event_interruptible(reader->wait,
+			event_available(buffer, reader) || reader->cancelled))
 		return -ERESTARTSYS;
 
 	if (!event_available(buffer, reader))
@@ -116,6 +119,12 @@
 	return event->data_size;
 }
 
+void ibmasm_cancel_next_event(struct event_reader *reader)
+{
+        reader->cancelled = 1;
+        wake_up_interruptible(&reader->wait);
+}
+
 void ibmasm_event_reader_register(struct service_processor *sp, struct event_reader *reader)
 {
 	unsigned long flags;
@@ -131,8 +140,6 @@
 {
 	unsigned long flags;
 
-	wake_up_interruptible(&reader->wait);
-
 	spin_lock_irqsave(&sp->lock, flags);
 	list_del(&reader->node);
 	spin_unlock_irqrestore(&sp->lock, flags);
@@ -164,6 +171,5 @@
 
 void ibmasm_event_buffer_exit(struct service_processor *sp)
 {
-	wake_up_event_readers(sp);
 	kfree(sp->event_buffer);
 }
diff --git a/drivers/misc/ibmasm/heartbeat.c b/drivers/misc/ibmasm/heartbeat.c
index ce09309..f295401 100644
--- a/drivers/misc/ibmasm/heartbeat.c
+++ b/drivers/misc/ibmasm/heartbeat.c
@@ -25,6 +25,7 @@
 #include <linux/notifier.h>
 #include "ibmasm.h"
 #include "dot_command.h"
+#include "lowlevel.h"
 
 static int suspend_heartbeats = 0;
 
@@ -62,7 +63,7 @@
 
 int ibmasm_heartbeat_init(struct service_processor *sp)
 {
-	sp->heartbeat = ibmasm_new_command(HEARTBEAT_BUFFER_SIZE);
+	sp->heartbeat = ibmasm_new_command(sp, HEARTBEAT_BUFFER_SIZE);
 	if (sp->heartbeat == NULL)
 		return -ENOMEM;
 
@@ -71,6 +72,12 @@
 
 void ibmasm_heartbeat_exit(struct service_processor *sp)
 {
+	char tsbuf[32];
+
+	dbg("%s:%d at %s\n", __FUNCTION__, __LINE__, get_timestamp(tsbuf));
+	ibmasm_wait_for_response(sp->heartbeat, IBMASM_CMD_TIMEOUT_NORMAL);
+	dbg("%s:%d at %s\n", __FUNCTION__, __LINE__, get_timestamp(tsbuf));
+	suspend_heartbeats = 1;
 	command_put(sp->heartbeat);
 }
 
@@ -78,14 +85,16 @@
 {
 	struct command *cmd = sp->heartbeat;
 	struct dot_command_header *header = (struct dot_command_header *)cmd->buffer;
+	char tsbuf[32];
 
+	dbg("%s:%d at %s\n", __FUNCTION__, __LINE__, get_timestamp(tsbuf));
 	if (suspend_heartbeats)
 		return;
 
 	/* return the received dot command to sender */
 	cmd->status = IBMASM_CMD_PENDING;
 	size = min(size, cmd->buffer_size);
-	memcpy(cmd->buffer, message, size);
+	memcpy_fromio(cmd->buffer, message, size);
 	header->type = sp_write;
 	ibmasm_exec_command(sp, cmd);
 }
diff --git a/drivers/misc/ibmasm/ibmasm.h b/drivers/misc/ibmasm/ibmasm.h
index 6fec7fd..ecce4ff 100644
--- a/drivers/misc/ibmasm/ibmasm.h
+++ b/drivers/misc/ibmasm/ibmasm.h
@@ -34,16 +34,31 @@
 #include <linux/version.h>
 #include <linux/interrupt.h>
 #include <linux/device.h>
+#include <linux/input.h>
 
 /* Driver identification */
 #define DRIVER_NAME	"ibmasm"
-#define DRIVER_VERSION  "0.4"
-#define DRIVER_AUTHOR   "Max Asbock"
+#define DRIVER_VERSION  "1.0"
+#define DRIVER_AUTHOR   "Max Asbock <masbock@us.ibm.com>, Vernon Mauery <vernux@us.ibm.com>"
 #define DRIVER_DESC     "IBM ASM Service Processor Driver"
 
 #define err(msg) printk(KERN_ERR "%s: " msg "\n", DRIVER_NAME)
 #define info(msg) printk(KERN_INFO "%s: " msg "\n", DRIVER_NAME)
 
+extern int ibmasm_debug;
+#define dbg(STR, ARGS...)					\
+	do {							\
+		if (ibmasm_debug)				\
+			printk(KERN_DEBUG STR , ##ARGS);	\
+	} while (0)
+
+static inline char *get_timestamp(char *buf)
+{
+	struct timeval now;
+	do_gettimeofday(&now);
+	sprintf(buf, "%lu.%lu", now.tv_sec, now.tv_usec);
+	return buf;
+}
 
 #define IBMASM_CMD_PENDING	0	
 #define IBMASM_CMD_COMPLETE	1	
@@ -52,7 +67,7 @@
 #define IBMASM_CMD_TIMEOUT_NORMAL	45
 #define IBMASM_CMD_TIMEOUT_EXTRA	240
 
-#define IBMASM_CMD_MAX_BUFFER_SIZE	0x4000
+#define IBMASM_CMD_MAX_BUFFER_SIZE	0x8000
 
 #define REVERSE_HEARTBEAT_TIMEOUT	120
 
@@ -80,12 +95,17 @@
 	size_t			buffer_size;
 	int			status;
 	struct kobject		kobj;
+	spinlock_t		*lock;
 };
 #define to_command(c) container_of(c, struct command, kobj)
 
 static inline void command_put(struct command *cmd)
 {
+	unsigned long flags;
+
+	spin_lock_irqsave(cmd->lock, flags);
         kobject_put(&cmd->kobj);
+	spin_unlock_irqrestore(cmd->lock, flags);
 }
 
 static inline void command_get(struct command *cmd)
@@ -108,6 +128,7 @@
 };
 
 struct event_reader {
+	int			cancelled;
 	unsigned int		next_serial_number;
 	wait_queue_head_t	wait;
 	struct list_head	node;
@@ -120,41 +141,11 @@
 	unsigned int		stopped;
 };
 
-
-/* remote console events */
-struct mouse_event {
-	long		x;
-	long		y;
-	unsigned char	buttons;
-	unsigned char	transitions;
+struct ibmasm_remote {
+	struct input_dev keybd_dev;
+	struct input_dev mouse_dev;
 };
 
-struct keyboard_event {
-	unsigned long	key_code;
-	unsigned char	key_down;
-};
-
-struct remote_event {
-	unsigned long	type;
-	union {
-		struct mouse_event	mouse;
-		struct keyboard_event	keyboard;
-	} data;
-};
-
-#define DRIVER_REMOTE_QUEUE_SIZE 240
-
-struct remote_queue {
-	struct remote_event	*start;
-	struct remote_event	*end;
-	struct remote_event	*reader;
-	struct remote_event	*writer;
-	unsigned int		size;
-	int			open;
-	wait_queue_head_t	wait;
-};
-
-
 struct service_processor {
 	struct list_head	node;
 	spinlock_t		lock;
@@ -167,13 +158,13 @@
 	char			dirname[IBMASM_NAME_SIZE];
 	char			devname[IBMASM_NAME_SIZE];
 	unsigned int		number;
-	struct remote_queue	remote_queue;
+	struct ibmasm_remote	*remote;
 	int			serial_line;
 	struct device		*dev;
 };
 
 /* command processing */
-extern struct command *ibmasm_new_command(size_t buffer_size);
+extern struct command *ibmasm_new_command(struct service_processor *sp, size_t buffer_size);
 extern void ibmasm_exec_command(struct service_processor *sp, struct command *cmd);
 extern void ibmasm_wait_for_response(struct command *cmd, int timeout);
 extern void ibmasm_receive_command_response(struct service_processor *sp, void *response,  size_t size);
@@ -185,6 +176,7 @@
 extern void ibmasm_event_reader_register(struct service_processor *sp, struct event_reader *reader);
 extern void ibmasm_event_reader_unregister(struct service_processor *sp, struct event_reader *reader);
 extern int ibmasm_get_next_event(struct service_processor *sp, struct event_reader *reader);
+extern void ibmasm_cancel_next_event(struct event_reader *reader);
 
 /* heartbeat - from SP to OS */
 extern void ibmasm_register_panic_notifier(void);
@@ -208,11 +200,9 @@
 extern irqreturn_t ibmasm_interrupt_handler(int irq, void * dev_id, struct pt_regs *regs);
 
 /* remote console */
-extern void ibmasm_handle_mouse_interrupt(struct service_processor *sp);
-extern int ibmasm_init_remote_queue(struct service_processor *sp);
-extern void ibmasm_free_remote_queue(struct service_processor *sp);
-extern void ibmasm_advance_reader(struct remote_queue *q, unsigned int n);
-extern size_t ibmasm_events_available(struct remote_queue *q);
+extern void ibmasm_handle_mouse_interrupt(struct service_processor *sp, struct pt_regs *regs);
+extern int ibmasm_init_remote_input_dev(struct service_processor *sp);
+extern void ibmasm_free_remote_input_dev(struct service_processor *sp);
 
 /* file system */
 extern int ibmasmfs_register(void);
diff --git a/drivers/misc/ibmasm/ibmasmfs.c b/drivers/misc/ibmasm/ibmasmfs.c
index 866e867..5c550fc 100644
--- a/drivers/misc/ibmasm/ibmasmfs.c
+++ b/drivers/misc/ibmasm/ibmasmfs.c
@@ -37,9 +37,7 @@
  *    |   |-- event
  *    |   |-- reverse_heartbeat
  *    |   `-- remote_video
- *    |       |-- connected
  *    |       |-- depth
- *    |       |-- events
  *    |       |-- height
  *    |       `-- width
  *    .
@@ -50,9 +48,7 @@
  *        |-- event
  *        |-- reverse_heartbeat
  *        `-- remote_video
- *            |-- connected
  *            |-- depth
- *            |-- events
  *            |-- height
  *            `-- width
  *
@@ -75,14 +71,6 @@
  * remote_video/width: control remote display settings
  * 	write: set value
  * 	read: read value
- *
- * remote_video/connected
- * 	read: return "1" if web browser VNC java applet is connected, 
- * 		"0" otherwise
- *
- * remote_video/events
- * 	read: sleep until a remote mouse or keyboard event occurs, then return
- * 		then event.
  */
 
 #include <linux/fs.h>
@@ -333,7 +321,7 @@
 	if (command_data->command)
 		return -EAGAIN;
 
-	cmd = ibmasm_new_command(count);
+	cmd = ibmasm_new_command(command_data->sp, count);
 	if (!cmd)
 		return -ENOMEM;
 
@@ -374,6 +362,7 @@
 	ibmasm_event_reader_register(sp, &event_data->reader);
 
 	event_data->sp = sp;
+	event_data->active = 0;
 	file->private_data = event_data;
 	return 0;
 }
@@ -391,7 +380,9 @@
 {
 	struct ibmasmfs_event_data *event_data = file->private_data;
 	struct event_reader *reader = &event_data->reader;
+	struct service_processor *sp = event_data->sp;
 	int ret;
+	unsigned long flags;
 
 	if (*offset < 0)
 		return -EINVAL;
@@ -400,17 +391,32 @@
 	if (*offset != 0)
 		return 0;
 
-	ret = ibmasm_get_next_event(event_data->sp, reader);
+	spin_lock_irqsave(&sp->lock, flags);
+	if (event_data->active) {
+		spin_unlock_irqrestore(&sp->lock, flags);
+		return -EBUSY;
+	}
+	event_data->active = 1;
+	spin_unlock_irqrestore(&sp->lock, flags);
+
+	ret = ibmasm_get_next_event(sp, reader);
 	if (ret <= 0)
-		return ret;
+		goto out;
 
-	if (count < reader->data_size)
-		return -EINVAL;
+	if (count < reader->data_size) {
+		ret = -EINVAL;
+		goto out;
+	}
 
-        if (copy_to_user(buf, reader->data, reader->data_size))
-		return -EFAULT;
+        if (copy_to_user(buf, reader->data, reader->data_size)) {
+		ret = -EFAULT;
+		goto out;
+	}
+	ret = reader->data_size;
 
-	return reader->data_size;
+out:
+	event_data->active = 0;
+	return ret;
 }
 
 static ssize_t event_file_write(struct file *file, const char __user *buf, size_t count, loff_t *offset)
@@ -424,7 +430,7 @@
 	if (*offset != 0)
 		return 0;
 
-	wake_up_interruptible(&event_data->reader.wait);
+	ibmasm_cancel_next_event(&event_data->reader);
 	return 0;
 }
 
@@ -575,75 +581,6 @@
 	return count;
 }
 
-static int remote_event_file_open(struct inode *inode, struct file *file)
-{
-	struct service_processor *sp;
-	unsigned long flags;
-	struct remote_queue *q;
-	
-	file->private_data = inode->u.generic_ip;
-	sp = file->private_data;
-	q = &sp->remote_queue;
-
-	/* allow only one event reader */
-	spin_lock_irqsave(&sp->lock, flags);
-	if (q->open) {
-		spin_unlock_irqrestore(&sp->lock, flags);
-		return -EBUSY;
-	}
-	q->open = 1;
-	spin_unlock_irqrestore(&sp->lock, flags);
-
-	enable_mouse_interrupts(sp);
-	
-	return 0;
-}
-
-static int remote_event_file_close(struct inode *inode, struct file *file)
-{
-	struct service_processor *sp = file->private_data;
-
-	disable_mouse_interrupts(sp);
-	wake_up_interruptible(&sp->remote_queue.wait);
-	sp->remote_queue.open = 0;
-
-	return 0;
-}
-
-static ssize_t remote_event_file_read(struct file *file, char __user *buf, size_t count, loff_t *offset)
-{
-	struct service_processor *sp = file->private_data;
-	struct remote_queue *q = &sp->remote_queue;
-	size_t data_size;
-	struct remote_event *reader = q->reader;
-	size_t num_events;
-
-	if (*offset < 0)
-		return -EINVAL;
-	if (count == 0 || count > 1024)
-		return 0;
-	if (*offset != 0)
-		return 0;
-
-	if (wait_event_interruptible(q->wait, q->reader != q->writer))
-		return -ERESTARTSYS;
-
-	/* only get multiples of struct remote_event */
-	num_events = min((count/sizeof(struct remote_event)), ibmasm_events_available(q));
-	if (!num_events)
-		return 0;
-
-	data_size = num_events * sizeof(struct remote_event);
-
-	if (copy_to_user(buf, reader, data_size))
-		return -EFAULT;
-
-	ibmasm_advance_reader(q, num_events);
-
-	return data_size;
-}
-
-
 static struct file_operations command_fops = {
 	.open =		command_file_open,
 	.release =	command_file_close,
@@ -672,12 +609,6 @@
 	.write =	remote_settings_file_write,
 };
 
-static struct file_operations remote_event_fops = {
-	.open =		remote_event_file_open,
-	.release =	remote_event_file_close,
-	.read =		remote_event_file_read,
-};
-
 
 static void ibmasmfs_create_files (struct super_block *sb, struct dentry *root)
 {
@@ -703,7 +634,5 @@
 		ibmasmfs_create_file(sb, remote_dir, "width", &remote_settings_fops, (void *)display_width(sp), S_IRUSR|S_IWUSR);
 		ibmasmfs_create_file(sb, remote_dir, "height", &remote_settings_fops, (void *)display_height(sp), S_IRUSR|S_IWUSR);
 		ibmasmfs_create_file(sb, remote_dir, "depth", &remote_settings_fops, (void *)display_depth(sp), S_IRUSR|S_IWUSR);
-		ibmasmfs_create_file(sb, remote_dir, "connected", &remote_settings_fops, (void *)vnc_status(sp), S_IRUSR);
-		ibmasmfs_create_file(sb, remote_dir, "events", &remote_event_fops, (void *)sp, S_IRUSR);
 	}
 }
diff --git a/drivers/misc/ibmasm/lowlevel.c b/drivers/misc/ibmasm/lowlevel.c
index 5156de2..47949a2 100644
--- a/drivers/misc/ibmasm/lowlevel.c
+++ b/drivers/misc/ibmasm/lowlevel.c
@@ -46,8 +46,8 @@
 
 	message = get_i2o_message(sp->base_address, mfa);
 
-	memcpy(&message->header, &header, sizeof(struct i2o_header));
-	memcpy(&message->data, command->buffer, command_size);
+	memcpy_toio(&message->header, &header, sizeof(struct i2o_header));
+	memcpy_toio(&message->data, command->buffer, command_size);
 
 	set_mfa_inbound(sp->base_address, mfa);
 
@@ -59,23 +59,27 @@
 	u32	mfa;
 	struct service_processor *sp = (struct service_processor *)dev_id;
 	void __iomem *base_address = sp->base_address;
+	char tsbuf[32];
 
 	if (!sp_interrupt_pending(base_address))
 		return IRQ_NONE;
 
+	dbg("respond to interrupt at %s\n", get_timestamp(tsbuf));
+
 	if (mouse_interrupt_pending(sp)) {
-		ibmasm_handle_mouse_interrupt(sp);
-		mfa = get_mfa_outbound(base_address);
+		ibmasm_handle_mouse_interrupt(sp, regs);
 		clear_mouse_interrupt(sp);
-		set_mfa_outbound(base_address, mfa);
-		return IRQ_HANDLED;
 	}
 
 	mfa = get_mfa_outbound(base_address);
 	if (valid_mfa(mfa)) {
 		struct i2o_message *msg = get_i2o_message(base_address, mfa);
 		ibmasm_receive_message(sp, &msg->data, incoming_data_size(msg));
-	}
+	} else
+		dbg("didn't get a valid MFA\n");
+
 	set_mfa_outbound(base_address, mfa);
+	dbg("finished interrupt at   %s\n", get_timestamp(tsbuf));
+
 	return IRQ_HANDLED;
 }
diff --git a/drivers/misc/ibmasm/module.c b/drivers/misc/ibmasm/module.c
index 777432a..1fdf03f 100644
--- a/drivers/misc/ibmasm/module.c
+++ b/drivers/misc/ibmasm/module.c
@@ -56,17 +56,26 @@
 #include "lowlevel.h"
 #include "remote.h"
 
+int ibmasm_debug = 0;
+module_param(ibmasm_debug, int , S_IRUGO | S_IWUSR);
+MODULE_PARM_DESC(ibmasm_debug, " Set debug mode on or off");
+
 
 static int __devinit ibmasm_init_one(struct pci_dev *pdev, const struct pci_device_id *id)
 {
-	int err, result = -ENOMEM;
+	int result;
 	struct service_processor *sp;
 
-	if ((err = pci_enable_device(pdev))) {
-		printk(KERN_ERR "%s: can't enable PCI device at %s\n",
-			DRIVER_NAME, pci_name(pdev));
-		return err;
+	if ((result = pci_enable_device(pdev))) {
+		dev_err(&pdev->dev, "Failed to enable PCI device\n");
+		return result;
 	}
+	if ((result = pci_request_regions(pdev, DRIVER_NAME))) {
+		dev_err(&pdev->dev, "Failed to allocate PCI resources\n");
+		goto error_resources;
+	}
+	/* vnc client won't work without bus-mastering */
+	pci_set_master(pdev);
 
 	sp = kmalloc(sizeof(struct service_processor), GFP_KERNEL);
 	if (sp == NULL) {
@@ -76,6 +85,9 @@
 	}
 	memset(sp, 0, sizeof(struct service_processor));
 
+	sp->lock = SPIN_LOCK_UNLOCKED;
+	INIT_LIST_HEAD(&sp->command_queue);
+
 	pci_set_drvdata(pdev, (void *)sp);
 	sp->dev = &pdev->dev;
 	sp->number = pdev->bus->number;
@@ -101,15 +113,6 @@
 		goto error_ioremap;
 	}
 
-	result = ibmasm_init_remote_queue(sp);
-	if (result) {
-		dev_err(sp->dev, "Failed to initialize remote queue\n");
-		goto error_remote_queue;
-	}
-
-	spin_lock_init(&sp->lock);
-	INIT_LIST_HEAD(&sp->command_queue);
-
 	result = request_irq(sp->irq, ibmasm_interrupt_handler, SA_SHIRQ, sp->devname, (void*)sp);
 	if (result) {
 		dev_err(sp->dev, "Failed to register interrupt handler\n");
@@ -117,7 +120,12 @@
 	}
 
 	enable_sp_interrupts(sp->base_address);
-	disable_mouse_interrupts(sp);
+
+	result = ibmasm_init_remote_input_dev(sp);
+	if (result) {
+		dev_err(sp->dev, "Failed to initialize remote queue\n");
+		goto error_send_message;
+	}
 
 	result = ibmasm_send_driver_vpd(sp);
 	if (result) {
@@ -133,30 +141,25 @@
 
 	ibmasm_register_uart(sp);
 
-	dev_printk(KERN_DEBUG, &pdev->dev, "WARNING: This software may not be supported or function\n");
-	dev_printk(KERN_DEBUG, &pdev->dev, "correctly on your IBM server. Please consult the IBM\n");
-	dev_printk(KERN_DEBUG, &pdev->dev, "ServerProven website\n");
-	dev_printk(KERN_DEBUG, &pdev->dev, "http://www.pc.ibm.com/ww/eserver/xseries/serverproven\n");
-	dev_printk(KERN_DEBUG, &pdev->dev, "for information on the specific driver level and support\n");
-	dev_printk(KERN_DEBUG, &pdev->dev, "statement for your IBM server.\n");
-
 	return 0;
 
 error_send_message:
 	disable_sp_interrupts(sp->base_address);
+	ibmasm_free_remote_input_dev(sp);
 	free_irq(sp->irq, (void *)sp);
 error_request_irq:
-	ibmasm_free_remote_queue(sp);
-error_remote_queue:
 	iounmap(sp->base_address);
 error_ioremap:
 	ibmasm_heartbeat_exit(sp);
 error_heartbeat:
 	ibmasm_event_buffer_exit(sp);
 error_eventbuffer:
+	pci_set_drvdata(pdev, NULL);
 	kfree(sp);
 error_kmalloc:
-	pci_disable_device(pdev);
+        pci_release_regions(pdev);
+error_resources:
+        pci_disable_device(pdev);
 
 	return result;
 }
@@ -165,16 +168,24 @@
 {
 	struct service_processor *sp = (struct service_processor *)pci_get_drvdata(pdev);
 
+	dbg("Unregistering UART\n");
 	ibmasm_unregister_uart(sp);
-	ibmasm_send_os_state(sp, SYSTEM_STATE_OS_DOWN);
-	disable_sp_interrupts(sp->base_address);
-	disable_mouse_interrupts(sp);
-	free_irq(sp->irq, (void *)sp);
+	dbg("Sending OS down message\n");
+	if (ibmasm_send_os_state(sp, SYSTEM_STATE_OS_DOWN))
+		err("failed to get repsonse to 'Send OS State' command\n");
+	dbg("Disabling heartbeats\n");
 	ibmasm_heartbeat_exit(sp);
-	ibmasm_free_remote_queue(sp);
+	dbg("Disabling interrupts\n");
+	disable_sp_interrupts(sp->base_address);
+	dbg("Freeing SP irq\n");
+	free_irq(sp->irq, (void *)sp);
+	dbg("Cleaning up\n");
+	ibmasm_free_remote_input_dev(sp);
 	iounmap(sp->base_address);
 	ibmasm_event_buffer_exit(sp);
+	pci_set_drvdata(pdev, NULL);
 	kfree(sp);
+	pci_release_regions(pdev);
 	pci_disable_device(pdev);
 }
 
diff --git a/drivers/misc/ibmasm/r_heartbeat.c b/drivers/misc/ibmasm/r_heartbeat.c
index 93d9c1b..f8fdb2d 100644
--- a/drivers/misc/ibmasm/r_heartbeat.c
+++ b/drivers/misc/ibmasm/r_heartbeat.c
@@ -63,7 +63,7 @@
 	int times_failed = 0;
 	int result = 1;
 
-	cmd = ibmasm_new_command(sizeof rhb_dot_cmd);
+	cmd = ibmasm_new_command(sp, sizeof rhb_dot_cmd);
 	if (!cmd)
 		return -ENOMEM;
 
diff --git a/drivers/misc/ibmasm/remote.c b/drivers/misc/ibmasm/remote.c
index 520c3f1..d3c48d2 100644
--- a/drivers/misc/ibmasm/remote.c
+++ b/drivers/misc/ibmasm/remote.c
@@ -1,4 +1,3 @@
-
 /*
  * IBM ASM Service Processor Device Driver
  *
@@ -18,120 +17,178 @@
  *
  * Copyright (C) IBM Corporation, 2004
  *
- * Author: Max Asböck <amax@us.ibm.com> 
+ * Authors: Max Asböck <amax@us.ibm.com>
+ *          Vernon Mauery <vernux@us.ibm.com>
  *
  */
 
 /* Remote mouse and keyboard event handling functions */
 
+#include <linux/pci.h>
 #include "ibmasm.h"
 #include "remote.h"
 
-int ibmasm_init_remote_queue(struct service_processor *sp)
+static int xmax = 1600;
+static int ymax = 1200;
+
+
+static unsigned short xlate_high[XLATE_SIZE] = {
+	[KEY_SYM_ENTER & 0xff] = KEY_ENTER,
+	[KEY_SYM_KPSLASH & 0xff] = KEY_KPSLASH,
+	[KEY_SYM_KPSTAR & 0xff] = KEY_KPASTERISK,
+	[KEY_SYM_KPMINUS & 0xff] = KEY_KPMINUS,
+	[KEY_SYM_KPDOT & 0xff] = KEY_KPDOT,
+	[KEY_SYM_KPPLUS & 0xff] = KEY_KPPLUS,
+	[KEY_SYM_KP0 & 0xff] = KEY_KP0,
+	[KEY_SYM_KP1 & 0xff] = KEY_KP1,
+	[KEY_SYM_KP2 & 0xff] = KEY_KP2, [KEY_SYM_KPDOWN & 0xff] = KEY_KP2,
+	[KEY_SYM_KP3 & 0xff] = KEY_KP3,
+	[KEY_SYM_KP4 & 0xff] = KEY_KP4, [KEY_SYM_KPLEFT & 0xff] = KEY_KP4,
+	[KEY_SYM_KP5 & 0xff] = KEY_KP5,
+	[KEY_SYM_KP6 & 0xff] = KEY_KP6, [KEY_SYM_KPRIGHT & 0xff] = KEY_KP6,
+	[KEY_SYM_KP7 & 0xff] = KEY_KP7,
+	[KEY_SYM_KP8 & 0xff] = KEY_KP8, [KEY_SYM_KPUP & 0xff] = KEY_KP8,
+	[KEY_SYM_KP9 & 0xff] = KEY_KP9,
+	[KEY_SYM_BK_SPC & 0xff] = KEY_BACKSPACE,
+	[KEY_SYM_TAB & 0xff] = KEY_TAB,
+	[KEY_SYM_CTRL & 0xff] = KEY_LEFTCTRL,
+	[KEY_SYM_ALT & 0xff] = KEY_LEFTALT,
+	[KEY_SYM_INSERT & 0xff] = KEY_INSERT,
+	[KEY_SYM_DELETE & 0xff] = KEY_DELETE,
+	[KEY_SYM_SHIFT & 0xff] = KEY_LEFTSHIFT,
+	[KEY_SYM_UARROW & 0xff] = KEY_UP,
+	[KEY_SYM_DARROW & 0xff] = KEY_DOWN,
+	[KEY_SYM_LARROW & 0xff] = KEY_LEFT,
+	[KEY_SYM_RARROW & 0xff] = KEY_RIGHT,
+	[KEY_SYM_ESCAPE & 0xff] = KEY_ESC,
+        [KEY_SYM_PAGEUP & 0xff] = KEY_PAGEUP,
+        [KEY_SYM_PAGEDOWN & 0xff] = KEY_PAGEDOWN,
+        [KEY_SYM_HOME & 0xff] = KEY_HOME,
+        [KEY_SYM_END & 0xff] = KEY_END,
+	[KEY_SYM_F1 & 0xff] = KEY_F1,
+	[KEY_SYM_F2 & 0xff] = KEY_F2,
+	[KEY_SYM_F3 & 0xff] = KEY_F3,
+	[KEY_SYM_F4 & 0xff] = KEY_F4,
+	[KEY_SYM_F5 & 0xff] = KEY_F5,
+	[KEY_SYM_F6 & 0xff] = KEY_F6,
+	[KEY_SYM_F7 & 0xff] = KEY_F7,
+	[KEY_SYM_F8 & 0xff] = KEY_F8,
+	[KEY_SYM_F9 & 0xff] = KEY_F9,
+	[KEY_SYM_F10 & 0xff] = KEY_F10,
+	[KEY_SYM_F11 & 0xff] = KEY_F11,
+	[KEY_SYM_F12 & 0xff] = KEY_F12,
+	[KEY_SYM_CAP_LOCK & 0xff] = KEY_CAPSLOCK,
+	[KEY_SYM_NUM_LOCK & 0xff] = KEY_NUMLOCK,
+	[KEY_SYM_SCR_LOCK & 0xff] = KEY_SCROLLLOCK,
+};
+static unsigned short xlate[XLATE_SIZE] = {
+	[NO_KEYCODE] = KEY_RESERVED,
+	[KEY_SYM_SPACE] = KEY_SPACE,
+	[KEY_SYM_TILDE] = KEY_GRAVE,        [KEY_SYM_BKTIC] = KEY_GRAVE,
+	[KEY_SYM_ONE] = KEY_1,              [KEY_SYM_BANG] = KEY_1,
+	[KEY_SYM_TWO] = KEY_2,              [KEY_SYM_AT] = KEY_2,
+	[KEY_SYM_THREE] = KEY_3,            [KEY_SYM_POUND] = KEY_3,
+	[KEY_SYM_FOUR] = KEY_4,             [KEY_SYM_DOLLAR] = KEY_4,
+	[KEY_SYM_FIVE] = KEY_5,             [KEY_SYM_PERCENT] = KEY_5,
+	[KEY_SYM_SIX] = KEY_6,              [KEY_SYM_CARAT] = KEY_6,
+	[KEY_SYM_SEVEN] = KEY_7,            [KEY_SYM_AMPER] = KEY_7,
+	[KEY_SYM_EIGHT] = KEY_8,            [KEY_SYM_STAR] = KEY_8,
+	[KEY_SYM_NINE] = KEY_9,             [KEY_SYM_LPAREN] = KEY_9,
+	[KEY_SYM_ZERO] = KEY_0,             [KEY_SYM_RPAREN] = KEY_0,
+	[KEY_SYM_MINUS] = KEY_MINUS,        [KEY_SYM_USCORE] = KEY_MINUS,
+	[KEY_SYM_EQUAL] = KEY_EQUAL,        [KEY_SYM_PLUS] = KEY_EQUAL,
+	[KEY_SYM_LBRKT] = KEY_LEFTBRACE,    [KEY_SYM_LCURLY] = KEY_LEFTBRACE,
+	[KEY_SYM_RBRKT] = KEY_RIGHTBRACE,   [KEY_SYM_RCURLY] = KEY_RIGHTBRACE,
+	[KEY_SYM_SLASH] = KEY_BACKSLASH,    [KEY_SYM_PIPE] = KEY_BACKSLASH,
+	[KEY_SYM_TIC] = KEY_APOSTROPHE,     [KEY_SYM_QUOTE] = KEY_APOSTROPHE,
+	[KEY_SYM_SEMIC] = KEY_SEMICOLON,    [KEY_SYM_COLON] = KEY_SEMICOLON,
+	[KEY_SYM_COMMA] = KEY_COMMA,        [KEY_SYM_LT] = KEY_COMMA,
+	[KEY_SYM_PERIOD] = KEY_DOT,         [KEY_SYM_GT] = KEY_DOT,
+	[KEY_SYM_BSLASH] = KEY_SLASH,       [KEY_SYM_QMARK] = KEY_SLASH,
+	[KEY_SYM_A] = KEY_A,                [KEY_SYM_a] = KEY_A,
+	[KEY_SYM_B] = KEY_B,                [KEY_SYM_b] = KEY_B,
+	[KEY_SYM_C] = KEY_C,                [KEY_SYM_c] = KEY_C,
+	[KEY_SYM_D] = KEY_D,                [KEY_SYM_d] = KEY_D,
+	[KEY_SYM_E] = KEY_E,                [KEY_SYM_e] = KEY_E,
+	[KEY_SYM_F] = KEY_F,                [KEY_SYM_f] = KEY_F,
+	[KEY_SYM_G] = KEY_G,                [KEY_SYM_g] = KEY_G,
+	[KEY_SYM_H] = KEY_H,                [KEY_SYM_h] = KEY_H,
+	[KEY_SYM_I] = KEY_I,                [KEY_SYM_i] = KEY_I,
+	[KEY_SYM_J] = KEY_J,                [KEY_SYM_j] = KEY_J,
+	[KEY_SYM_K] = KEY_K,                [KEY_SYM_k] = KEY_K,
+	[KEY_SYM_L] = KEY_L,                [KEY_SYM_l] = KEY_L,
+	[KEY_SYM_M] = KEY_M,                [KEY_SYM_m] = KEY_M,
+	[KEY_SYM_N] = KEY_N,                [KEY_SYM_n] = KEY_N,
+	[KEY_SYM_O] = KEY_O,                [KEY_SYM_o] = KEY_O,
+	[KEY_SYM_P] = KEY_P,                [KEY_SYM_p] = KEY_P,
+	[KEY_SYM_Q] = KEY_Q,                [KEY_SYM_q] = KEY_Q,
+	[KEY_SYM_R] = KEY_R,                [KEY_SYM_r] = KEY_R,
+	[KEY_SYM_S] = KEY_S,                [KEY_SYM_s] = KEY_S,
+	[KEY_SYM_T] = KEY_T,                [KEY_SYM_t] = KEY_T,
+	[KEY_SYM_U] = KEY_U,                [KEY_SYM_u] = KEY_U,
+	[KEY_SYM_V] = KEY_V,                [KEY_SYM_v] = KEY_V,
+	[KEY_SYM_W] = KEY_W,                [KEY_SYM_w] = KEY_W,
+	[KEY_SYM_X] = KEY_X,                [KEY_SYM_x] = KEY_X,
+	[KEY_SYM_Y] = KEY_Y,                [KEY_SYM_y] = KEY_Y,
+	[KEY_SYM_Z] = KEY_Z,                [KEY_SYM_z] = KEY_Z,
+};
+
+static char remote_mouse_name[] = "ibmasm RSA I remote mouse";
+static char remote_keybd_name[] = "ibmasm RSA I remote keyboard";
+
+static void print_input(struct remote_input *input)
 {
-	struct remote_queue *q = &sp->remote_queue;
-
-	disable_mouse_interrupts(sp);
-
-	q->open = 0;
-	q->size = 0;
-
-	q->start = kmalloc(DRIVER_REMOTE_QUEUE_SIZE * sizeof(struct remote_event), GFP_KERNEL);
-        if (q->start == 0)
-                return -ENOMEM;
-
-	q->end = q->start + DRIVER_REMOTE_QUEUE_SIZE;
-	q->reader = q->start;
-	q->writer = q->start;
-	q->size = DRIVER_REMOTE_QUEUE_SIZE;
-	init_waitqueue_head(&q->wait);
-
-	return 0;
-}
-
-void ibmasm_free_remote_queue(struct service_processor *sp)
-{
-	kfree(sp->remote_queue.start);
-}
-
-void ibmasm_advance_reader(struct remote_queue *q, unsigned int n)
-{
-	q->reader += n;
-	if (q->reader >= q->end)
-		q->reader -= q->size;
-}
-
-size_t ibmasm_events_available(struct remote_queue *q)
-{
-	ssize_t diff = q->writer - q->reader;
- 
-	return (diff >= 0) ? diff : q->end - q->reader;	
-}
-	
-
-static int space_free(struct remote_queue *q)
-{
-	if (q->reader == q->writer)
-		return q->size - 1;
-
-	return ( (q->reader + q->size - q->writer) % q->size ) - 1;
-}
-
-static void set_mouse_event(struct remote_input *input, struct mouse_event *mouse)
-{
-	static char last_buttons = 0;
-
-	mouse->x = input->data.mouse.x;
-	mouse->y = input->data.mouse.y;
-
-	if (input->mouse_buttons == REMOTE_MOUSE_DOUBLE_CLICK) {
-		mouse->buttons = REMOTE_MOUSE_DOUBLE_CLICK;
-		last_buttons = 0;
-		return;
+	if (input->type == INPUT_TYPE_MOUSE) {
+		unsigned char buttons = input->mouse_buttons;
+		dbg("remote mouse movement: (x,y)=(%d,%d)%s%s%s%s\n",
+			input->data.mouse.x, input->data.mouse.y,
+			(buttons)?" -- buttons:":"",
+			(buttons & REMOTE_BUTTON_LEFT)?"left ":"",
+			(buttons & REMOTE_BUTTON_MIDDLE)?"middle ":"",
+			(buttons & REMOTE_BUTTON_RIGHT)?"right":""
+		      );
+	} else {
+		dbg("remote keypress (code, flag, down):"
+			   "%d (0x%x) [0x%x] [0x%x]\n",
+				input->data.keyboard.key_code,
+				input->data.keyboard.key_code,
+				input->data.keyboard.key_flag,
+				input->data.keyboard.key_down
+		      );
 	}
-	mouse->transitions = last_buttons ^ input->mouse_buttons;
-	mouse->buttons = input->mouse_buttons;
-
-	last_buttons = input->mouse_buttons;
 }
 
-static void set_keyboard_event(struct remote_input *input, struct keyboard_event *keyboard)
+static void send_mouse_event(struct input_dev *dev, struct pt_regs *regs,
+		struct remote_input *input)
 {
-	keyboard->key_code = input->data.keyboard.key_code;
-	keyboard->key_down = input->data.keyboard.key_down;
+	unsigned char buttons = input->mouse_buttons;
+
+	input_regs(dev, regs);
+	input_report_abs(dev, ABS_X, input->data.mouse.x);
+	input_report_abs(dev, ABS_Y, input->data.mouse.y);
+	input_report_key(dev, BTN_LEFT, buttons & REMOTE_BUTTON_LEFT);
+	input_report_key(dev, BTN_MIDDLE, buttons & REMOTE_BUTTON_MIDDLE);
+	input_report_key(dev, BTN_RIGHT, buttons & REMOTE_BUTTON_RIGHT);
+	input_sync(dev);
 }
 
-static int add_to_driver_queue(struct remote_queue *q, struct remote_input *input)
+static void send_keyboard_event(struct input_dev *dev, struct pt_regs *regs,
+		struct remote_input *input)
 {
-	struct remote_event *event = q->writer;
+	unsigned int key;
+	unsigned short code = input->data.keyboard.key_code;
 
-	if (space_free(q) < 1) {
-		return 1;
-	}
-
-	switch(input->type) {
-	case (INPUT_TYPE_MOUSE):
-		event->type = INPUT_TYPE_MOUSE;
-		set_mouse_event(input, &event->data.mouse);
-		break;
-	case (INPUT_TYPE_KEYBOARD):
-		event->type = INPUT_TYPE_KEYBOARD;
-		set_keyboard_event(input, &event->data.keyboard);
-		break;
-	default:
-		return 0;
-	}
-	event->type = input->type;
-
-	q->writer++;
-	if (q->writer == q->end)
-		q->writer = q->start;
-
-	return 0;
+	if (code & 0xff00)
+		key = xlate_high[code & 0xff];
+	else
+		key = xlate[code];
+	input_regs(dev, regs);
+	input_report_key(dev, key, (input->data.keyboard.key_down) ? 1 : 0);
+	input_sync(dev);
 }
-	
 
-void ibmasm_handle_mouse_interrupt(struct service_processor *sp)
+void ibmasm_handle_mouse_interrupt(struct service_processor *sp,
+		struct pt_regs *regs)
 {
 	unsigned long reader;
 	unsigned long writer;
@@ -141,12 +198,75 @@
 	writer = get_queue_writer(sp);
 
 	while (reader != writer) {
-		memcpy(&input, (void *)get_queue_entry(sp, reader), sizeof(struct remote_input));
+		memcpy_fromio(&input, get_queue_entry(sp, reader),
+				sizeof(struct remote_input));
 
-		if (add_to_driver_queue(&sp->remote_queue, &input))
+		print_input(&input);
+		if (input.type == INPUT_TYPE_MOUSE) {
+			send_mouse_event(&sp->remote->mouse_dev, regs, &input);
+		} else if (input.type == INPUT_TYPE_KEYBOARD) {
+			send_keyboard_event(&sp->remote->keybd_dev, regs, &input);
+		} else
 			break;
 
 		reader = advance_queue_reader(sp, reader);
+		writer = get_queue_writer(sp);
 	}
-	wake_up_interruptible(&sp->remote_queue.wait);
 }
+
+int ibmasm_init_remote_input_dev(struct service_processor *sp)
+{
+	/* set up the mouse input device */
+	struct ibmasm_remote *remote;
+	struct pci_dev *pdev = to_pci_dev(sp->dev);
+	int i;
+
+	sp->remote = remote = kmalloc(sizeof(*remote), GFP_KERNEL);
+	if (!remote)
+		return -ENOMEM;
+
+	memset(remote, 0, sizeof(*remote));
+
+	remote->mouse_dev.private = remote;
+	init_input_dev(&remote->mouse_dev);
+	remote->mouse_dev.id.vendor = pdev->vendor;
+	remote->mouse_dev.id.product = pdev->device;
+	remote->mouse_dev.evbit[0]  = BIT(EV_KEY) | BIT(EV_ABS);
+	remote->mouse_dev.keybit[LONG(BTN_MOUSE)] = BIT(BTN_LEFT) |
+		BIT(BTN_RIGHT) | BIT(BTN_MIDDLE);
+	set_bit(BTN_TOUCH, remote->mouse_dev.keybit);
+	remote->mouse_dev.name = remote_mouse_name;
+	input_set_abs_params(&remote->mouse_dev, ABS_X, 0, xmax, 0, 0);
+	input_set_abs_params(&remote->mouse_dev, ABS_Y, 0, ymax, 0, 0);
+
+	remote->keybd_dev.private = remote;
+	init_input_dev(&remote->keybd_dev);
+	remote->keybd_dev.id.vendor = pdev->vendor;
+	remote->keybd_dev.id.product = pdev->device;
+	remote->keybd_dev.evbit[0]  = BIT(EV_KEY);
+	remote->keybd_dev.name = remote_keybd_name;
+
+	for (i=0; i<XLATE_SIZE; i++) {
+		if (xlate_high[i])
+			set_bit(xlate_high[i], remote->keybd_dev.keybit);
+		if (xlate[i])
+			set_bit(xlate[i], remote->keybd_dev.keybit);
+	}
+
+	input_register_device(&remote->mouse_dev);
+	input_register_device(&remote->keybd_dev);
+	enable_mouse_interrupts(sp);
+
+	printk(KERN_INFO "ibmasm remote responding to events on RSA card %d\n", sp->number);
+
+	return 0;
+}
+
+void ibmasm_free_remote_input_dev(struct service_processor *sp)
+{
+	disable_mouse_interrupts(sp);
+	input_unregister_device(&sp->remote->keybd_dev);
+	input_unregister_device(&sp->remote->mouse_dev);
+	kfree(sp->remote);
+}
+
diff --git a/drivers/misc/ibmasm/remote.h b/drivers/misc/ibmasm/remote.h
index a8eb19f..b7076a8 100644
--- a/drivers/misc/ibmasm/remote.h
+++ b/drivers/misc/ibmasm/remote.h
@@ -51,11 +51,13 @@
 
 
 /* mouse button states received from SP */
-#define REMOTE_MOUSE_DOUBLE_CLICK	0xF0
-#define REMOTE_MOUSE_BUTTON_LEFT	0x01
-#define REMOTE_MOUSE_BUTTON_MIDDLE	0x02
-#define REMOTE_MOUSE_BUTTON_RIGHT	0x04
+#define REMOTE_DOUBLE_CLICK	0xF0
+#define REMOTE_BUTTON_LEFT	0x01
+#define REMOTE_BUTTON_MIDDLE	0x02
+#define REMOTE_BUTTON_RIGHT	0x04
 
+/* size of keysym/keycode translation matricies */
+#define XLATE_SIZE 256
 
 struct mouse_input {
 	unsigned short	y;
@@ -83,11 +85,13 @@
 	unsigned char	pad3;
 };
 
-#define mouse_addr(sp) 		sp->base_address + CONDOR_MOUSE_DATA
-#define display_width(sp)	mouse_addr(sp) + CONDOR_INPUT_DISPLAY_RESX
-#define display_height(sp)	mouse_addr(sp) + CONDOR_INPUT_DISPLAY_RESY
-#define display_depth(sp)	mouse_addr(sp) + CONDOR_INPUT_DISPLAY_BITS
-#define vnc_status(sp)		mouse_addr(sp) + CONDOR_OUTPUT_VNC_STATUS
+#define mouse_addr(sp) 		(sp->base_address + CONDOR_MOUSE_DATA)
+#define display_width(sp)	(mouse_addr(sp) + CONDOR_INPUT_DISPLAY_RESX)
+#define display_height(sp)	(mouse_addr(sp) + CONDOR_INPUT_DISPLAY_RESY)
+#define display_depth(sp)	(mouse_addr(sp) + CONDOR_INPUT_DISPLAY_BITS)
+#define desktop_info(sp)	(mouse_addr(sp) + CONDOR_INPUT_DESKTOP_INFO)
+#define vnc_status(sp)		(mouse_addr(sp) + CONDOR_OUTPUT_VNC_STATUS)
+#define isr_control(sp)		(mouse_addr(sp) + CONDOR_MOUSE_ISR_CONTROL)
 
 #define mouse_interrupt_pending(sp) 	readl(mouse_addr(sp) + CONDOR_MOUSE_ISR_STATUS)
 #define clear_mouse_interrupt(sp)	writel(0, mouse_addr(sp) + CONDOR_MOUSE_ISR_STATUS)
@@ -101,10 +105,10 @@
 #define get_queue_reader(sp)	readl(mouse_addr(sp) + CONDOR_MOUSE_Q_READER)
 #define set_queue_reader(sp, reader)	writel(reader, mouse_addr(sp) + CONDOR_MOUSE_Q_READER)
 
-#define queue_begin	mouse_addr(sp) + CONDOR_MOUSE_Q_BEGIN
+#define queue_begin	(mouse_addr(sp) + CONDOR_MOUSE_Q_BEGIN)
 
 #define get_queue_entry(sp, read_index) \
-	queue_begin + read_index * sizeof(struct remote_input)
+	((void*)(queue_begin + read_index * sizeof(struct remote_input)))
 
 static inline int advance_queue_reader(struct service_processor *sp, unsigned long reader)
 {
@@ -116,4 +120,151 @@
 	return reader;
 }
 
+#define NO_KEYCODE 0
+#define KEY_SYM_BK_SPC   0xFF08
+#define KEY_SYM_TAB      0xFF09
+#define KEY_SYM_ENTER    0xFF0D
+#define KEY_SYM_SCR_LOCK 0xFF14
+#define KEY_SYM_ESCAPE   0xFF1B
+#define KEY_SYM_HOME     0xFF50
+#define KEY_SYM_LARROW   0xFF51
+#define KEY_SYM_UARROW   0xFF52
+#define KEY_SYM_RARROW   0xFF53
+#define KEY_SYM_DARROW   0xFF54
+#define KEY_SYM_PAGEUP   0xFF55
+#define KEY_SYM_PAGEDOWN 0xFF56
+#define KEY_SYM_END      0xFF57
+#define KEY_SYM_INSERT   0xFF63
+#define KEY_SYM_NUM_LOCK 0xFF7F
+#define KEY_SYM_KPSTAR   0xFFAA
+#define KEY_SYM_KPPLUS   0xFFAB
+#define KEY_SYM_KPMINUS  0xFFAD
+#define KEY_SYM_KPDOT    0xFFAE
+#define KEY_SYM_KPSLASH  0xFFAF
+#define KEY_SYM_KPRIGHT  0xFF96
+#define KEY_SYM_KPUP     0xFF97
+#define KEY_SYM_KPLEFT   0xFF98
+#define KEY_SYM_KPDOWN   0xFF99
+#define KEY_SYM_KP0      0xFFB0
+#define KEY_SYM_KP1      0xFFB1
+#define KEY_SYM_KP2      0xFFB2
+#define KEY_SYM_KP3      0xFFB3
+#define KEY_SYM_KP4      0xFFB4
+#define KEY_SYM_KP5      0xFFB5
+#define KEY_SYM_KP6      0xFFB6
+#define KEY_SYM_KP7      0xFFB7
+#define KEY_SYM_KP8      0xFFB8
+#define KEY_SYM_KP9      0xFFB9
+#define KEY_SYM_F1       0xFFBE      // 1B 5B 5B 41
+#define KEY_SYM_F2       0xFFBF      // 1B 5B 5B 42
+#define KEY_SYM_F3       0xFFC0      // 1B 5B 5B 43
+#define KEY_SYM_F4       0xFFC1      // 1B 5B 5B 44
+#define KEY_SYM_F5       0xFFC2      // 1B 5B 5B 45
+#define KEY_SYM_F6       0xFFC3      // 1B 5B 31 37 7E
+#define KEY_SYM_F7       0xFFC4      // 1B 5B 31 38 7E
+#define KEY_SYM_F8       0xFFC5      // 1B 5B 31 39 7E
+#define KEY_SYM_F9       0xFFC6      // 1B 5B 32 30 7E
+#define KEY_SYM_F10      0xFFC7      // 1B 5B 32 31 7E
+#define KEY_SYM_F11      0xFFC8      // 1B 5B 32 33 7E
+#define KEY_SYM_F12      0xFFC9      // 1B 5B 32 34 7E
+#define KEY_SYM_SHIFT    0xFFE1
+#define KEY_SYM_CTRL     0xFFE3
+#define KEY_SYM_ALT      0xFFE9
+#define KEY_SYM_CAP_LOCK 0xFFE5
+#define KEY_SYM_DELETE   0xFFFF
+#define KEY_SYM_TILDE    0x60
+#define KEY_SYM_BKTIC    0x7E
+#define KEY_SYM_ONE      0x31
+#define KEY_SYM_BANG     0x21
+#define KEY_SYM_TWO      0x32
+#define KEY_SYM_AT       0x40
+#define KEY_SYM_THREE    0x33
+#define KEY_SYM_POUND    0x23
+#define KEY_SYM_FOUR     0x34
+#define KEY_SYM_DOLLAR   0x24
+#define KEY_SYM_FIVE     0x35
+#define KEY_SYM_PERCENT  0x25
+#define KEY_SYM_SIX      0x36
+#define KEY_SYM_CARAT    0x5E
+#define KEY_SYM_SEVEN    0x37
+#define KEY_SYM_AMPER    0x26
+#define KEY_SYM_EIGHT    0x38
+#define KEY_SYM_STAR     0x2A
+#define KEY_SYM_NINE     0x39
+#define KEY_SYM_LPAREN   0x28
+#define KEY_SYM_ZERO     0x30
+#define KEY_SYM_RPAREN   0x29
+#define KEY_SYM_MINUS    0x2D
+#define KEY_SYM_USCORE   0x5F
+#define KEY_SYM_EQUAL    0x2B
+#define KEY_SYM_PLUS     0x3D
+#define KEY_SYM_LBRKT    0x5B
+#define KEY_SYM_LCURLY   0x7B
+#define KEY_SYM_RBRKT    0x5D
+#define KEY_SYM_RCURLY   0x7D
+#define KEY_SYM_SLASH    0x5C
+#define KEY_SYM_PIPE     0x7C
+#define KEY_SYM_TIC      0x27
+#define KEY_SYM_QUOTE    0x22
+#define KEY_SYM_SEMIC    0x3B
+#define KEY_SYM_COLON    0x3A
+#define KEY_SYM_COMMA    0x2C
+#define KEY_SYM_LT       0x3C
+#define KEY_SYM_PERIOD   0x2E
+#define KEY_SYM_GT       0x3E
+#define KEY_SYM_BSLASH   0x2F
+#define KEY_SYM_QMARK    0x3F
+#define KEY_SYM_A        0x41
+#define KEY_SYM_B        0x42
+#define KEY_SYM_C        0x43
+#define KEY_SYM_D        0x44
+#define KEY_SYM_E        0x45
+#define KEY_SYM_F        0x46
+#define KEY_SYM_G        0x47
+#define KEY_SYM_H        0x48
+#define KEY_SYM_I        0x49
+#define KEY_SYM_J        0x4A
+#define KEY_SYM_K        0x4B
+#define KEY_SYM_L        0x4C
+#define KEY_SYM_M        0x4D
+#define KEY_SYM_N        0x4E
+#define KEY_SYM_O        0x4F
+#define KEY_SYM_P        0x50
+#define KEY_SYM_Q        0x51
+#define KEY_SYM_R        0x52
+#define KEY_SYM_S        0x53
+#define KEY_SYM_T        0x54
+#define KEY_SYM_U        0x55
+#define KEY_SYM_V        0x56
+#define KEY_SYM_W        0x57
+#define KEY_SYM_X        0x58
+#define KEY_SYM_Y        0x59
+#define KEY_SYM_Z        0x5A
+#define KEY_SYM_a        0x61
+#define KEY_SYM_b        0x62
+#define KEY_SYM_c        0x63
+#define KEY_SYM_d        0x64
+#define KEY_SYM_e        0x65
+#define KEY_SYM_f        0x66
+#define KEY_SYM_g        0x67
+#define KEY_SYM_h        0x68
+#define KEY_SYM_i        0x69
+#define KEY_SYM_j        0x6A
+#define KEY_SYM_k        0x6B
+#define KEY_SYM_l        0x6C
+#define KEY_SYM_m        0x6D
+#define KEY_SYM_n        0x6E
+#define KEY_SYM_o        0x6F
+#define KEY_SYM_p        0x70
+#define KEY_SYM_q        0x71
+#define KEY_SYM_r        0x72
+#define KEY_SYM_s        0x73
+#define KEY_SYM_t        0x74
+#define KEY_SYM_u        0x75
+#define KEY_SYM_v        0x76
+#define KEY_SYM_w        0x77
+#define KEY_SYM_x        0x78
+#define KEY_SYM_y        0x79
+#define KEY_SYM_z        0x7A
+#define KEY_SYM_SPACE    0x20
 #endif /* _IBMASM_REMOTE_H_ */
diff --git a/drivers/net/3c59x.c b/drivers/net/3c59x.c
index b5e0760..80ec9aa 100644
--- a/drivers/net/3c59x.c
+++ b/drivers/net/3c59x.c
@@ -2202,9 +2202,8 @@
 
 	if (vortex_debug > 6) {
 		printk(KERN_DEBUG "boomerang_start_xmit()\n");
-		if (vortex_debug > 3)
-			printk(KERN_DEBUG "%s: Trying to send a packet, Tx index %d.\n",
-				   dev->name, vp->cur_tx);
+		printk(KERN_DEBUG "%s: Trying to send a packet, Tx index %d.\n",
+			   dev->name, vp->cur_tx);
 	}
 
 	if (vp->cur_tx - vp->dirty_tx >= TX_RING_SIZE) {
diff --git a/drivers/net/8390.c b/drivers/net/8390.c
index bab16bc..6d76f3a 100644
--- a/drivers/net/8390.c
+++ b/drivers/net/8390.c
@@ -225,9 +225,9 @@
 	unsigned long icucr;
 
 	local_irq_save(flags);
-	icucr = inl(ICUCR1);
+	icucr = inl(M32R_ICU_CR1_PORTL);
 	icucr |= M32R_ICUCR_ISMOD11;
-	outl(icucr, ICUCR1);
+	outl(icucr, M32R_ICU_CR1_PORTL);
 	local_irq_restore(flags);
 #endif
 	ei_local->stat.tx_errors++;
diff --git a/drivers/oprofile/buffer_sync.c b/drivers/oprofile/buffer_sync.c
index 55720dc..745a141 100644
--- a/drivers/oprofile/buffer_sync.c
+++ b/drivers/oprofile/buffer_sync.c
@@ -62,7 +62,7 @@
 	/* To avoid latency problems, we only process the current CPU,
 	 * hoping that most samples for the task are on this CPU
 	 */
-	sync_buffer(_smp_processor_id());
+	sync_buffer(raw_smp_processor_id());
   	return 0;
 }
 
@@ -86,7 +86,7 @@
 		/* To avoid latency problems, we only process the current CPU,
 		 * hoping that most samples for the task are on this CPU
 		 */
-		sync_buffer(_smp_processor_id());
+		sync_buffer(raw_smp_processor_id());
 		return 0;
 	}
 
diff --git a/drivers/pcmcia/Kconfig b/drivers/pcmcia/Kconfig
index 6375ebc..14e4124 100644
--- a/drivers/pcmcia/Kconfig
+++ b/drivers/pcmcia/Kconfig
@@ -171,19 +171,21 @@
 config M32R_PCC
 	bool "M32R PCMCIA I/F"
 	depends on M32R && CHIP_M32700 && PCMCIA
+	select PCCARD_NONSTATIC
 	help
 	  Say Y here to use the M32R PCMCIA controller.
 
 config M32R_CFC
 	bool "M32R CF I/F Controller"
-	depends on M32R && (PLAT_USRV || PLAT_M32700UT || PLAT_MAPPI2 || PLAT_OPSPUT)
+	depends on M32R && (PLAT_USRV || PLAT_M32700UT || PLAT_MAPPI2 || PLAT_MAPPI3 || PLAT_OPSPUT)
+	select PCCARD_NONSTATIC
 	help
 	  Say Y here to use the M32R CompactFlash controller.
 
 config M32R_CFC_NUM
 	int "M32R CF I/F number"
 	depends on M32R_CFC
-	default "1" if PLAT_USRV || PLAT_M32700UT || PLAT_MAPPI2 || PLAT_OPSPUT
+	default "1" if PLAT_USRV || PLAT_M32700UT || PLAT_MAPPI2 || PLAT_MAPPI3 || PLAT_OPSPUT
 	help
 	  Set the number of M32R CF slots.
 
diff --git a/drivers/pcmcia/m32r_cfc.c b/drivers/pcmcia/m32r_cfc.c
index 581bfa9..b1111c6 100644
--- a/drivers/pcmcia/m32r_cfc.c
+++ b/drivers/pcmcia/m32r_cfc.c
@@ -24,9 +24,9 @@
 #include <linux/workqueue.h>
 #include <linux/interrupt.h>
 #include <linux/device.h>
+#include <linux/bitops.h>
 #include <asm/irq.h>
 #include <asm/io.h>
-#include <asm/bitops.h>
 #include <asm/system.h>
 
 #include <pcmcia/version.h>
@@ -444,7 +444,7 @@
 		debug(3, "m32r_cfc: _pcc_get_status: "
 			 "power off (CPCR=0x%08x)\n", status);
 	}
-#elif defined(CONFIG_PLAT_MAPPI2)
+#elif defined(CONFIG_PLAT_MAPPI2) || defined(CONFIG_PLAT_MAPPI3)
 	if ( status ) {
 		status = pcc_get(sock, (unsigned int)PLD_CPCR);
 		if (status == 0) { /* power off */
@@ -452,18 +452,23 @@
 			pcc_set(sock, (unsigned int)PLD_CFBUFCR,0); /* force buffer off for ZA-36 */
 			udelay(50);
 		}
-		status = pcc_get(sock, (unsigned int)PLD_CFBUFCR);
-		if (status != 0) { /* buffer off */
-			pcc_set(sock, (unsigned int)PLD_CFBUFCR,0);
-			udelay(50);
-			pcc_set(sock, (unsigned int)PLD_CFRSTCR, 0x0101);
-			udelay(25); /* for IDE reset */
-			pcc_set(sock, (unsigned int)PLD_CFRSTCR, 0x0100);
-			mdelay(2);  /* for IDE reset */
-		} else {
-			*value |= SS_POWERON;
-			*value |= SS_READY;
-		}
+		*value |= SS_POWERON;
+
+		pcc_set(sock, (unsigned int)PLD_CFBUFCR,0);
+		udelay(50);
+		pcc_set(sock, (unsigned int)PLD_CFRSTCR, 0x0101);
+		udelay(25); /* for IDE reset */
+		pcc_set(sock, (unsigned int)PLD_CFRSTCR, 0x0100);
+		mdelay(2);  /* for IDE reset */
+
+		*value |= SS_READY;
+		*value |= SS_3VCARD;
+	} else {
+		/* disable CF power */
+	        pcc_set(sock, (unsigned int)PLD_CPCR, 0);
+		udelay(100);
+		debug(3, "m32r_cfc: _pcc_get_status: "
+			 "power off (CPCR=0x%08x)\n", status);
 	}
 #else
 #error no platform configuration
@@ -479,14 +484,13 @@
 {
 //	pcc_socket_t *t = &socket[sock];
 
-#if defined(CONFIG_PLAT_M32700UT) || defined(CONFIG_PLAT_USRV) || defined(CONFIG_PLAT_OPSPUT)
 	state->flags = 0;
 	state->csc_mask = SS_DETECT;
 	state->csc_mask |= SS_READY;
 	state->io_irq = 0;
 	state->Vcc = 33;	/* 3.3V fixed */
 	state->Vpp = 33;
-#endif
+
 	debug(3, "m32r_cfc: GetSocket(%d) = flags %#3.3x, Vcc %d, Vpp %d, "
 		  "io_irq %d, csc_mask %#2.2x\n", sock, state->flags,
 		  state->Vcc, state->Vpp, state->io_irq, state->csc_mask);
@@ -497,32 +501,17 @@
 
 static int _pcc_set_socket(u_short sock, socket_state_t *state)
 {
-#if defined(CONFIG_PLAT_MAPPI2)
-	u_long reg = 0;
-#endif
 	debug(3, "m32r_cfc: SetSocket(%d, flags %#3.3x, Vcc %d, Vpp %d, "
 		  "io_irq %d, csc_mask %#2.2x)\n", sock, state->flags,
 		  state->Vcc, state->Vpp, state->io_irq, state->csc_mask);
 
-#if defined(CONFIG_PLAT_M32700UT) || defined(CONFIG_PLAT_USRV) || defined(CONFIG_PLAT_OPSPUT)
+#if defined(CONFIG_PLAT_M32700UT) || defined(CONFIG_PLAT_USRV) || defined(CONFIG_PLAT_OPSPUT) || defined(CONFIG_PLAT_MAPPI2) || defined(CONFIG_PLAT_MAPPI3)
 	if (state->Vcc) {
 		if ((state->Vcc != 50) && (state->Vcc != 33))
 			return -EINVAL;
 		/* accept 5V and 3.3V */
 	}
-#elif defined(CONFIG_PLAT_MAPPI2)
-	if (state->Vcc) {
-		/*
-		 * 5V only
-		 */
-		if (state->Vcc == 50) {
-			reg |= PCCSIGCR_VEN;
-		} else {
-			return -EINVAL;
-		}
-	}
 #endif
-
 	if (state->flags & SS_RESET) {
 		debug(3, ":RESET\n");
 		pcc_set(sock,(unsigned int)PLD_CFRSTCR,0x101);
@@ -788,7 +777,7 @@
 		return ret;
 	}
 
-#if defined(CONFIG_PLAT_MAPPI2)
+#if defined(CONFIG_PLAT_MAPPI2) || defined(CONFIG_PLAT_MAPPI3)
 	pcc_set(0, (unsigned int)PLD_CFCR0, 0x0f0f);
 	pcc_set(0, (unsigned int)PLD_CFCR1, 0x0200);
 #endif
@@ -825,7 +814,7 @@
 	for (i = 0 ; i < pcc_sockets ; i++) {
 		socket[i].socket.dev.dev = &pcc_device.dev;
 		socket[i].socket.ops = &pcc_operations;
-		socket[i].socket.resource_ops = &pccard_static_ops;
+		socket[i].socket.resource_ops = &pccard_nonstatic_ops;
 		socket[i].socket.owner = THIS_MODULE;
 		socket[i].number = i;
 		ret = pcmcia_register_socket(&socket[i].socket);
diff --git a/drivers/pcmcia/m32r_cfc.h b/drivers/pcmcia/m32r_cfc.h
index 17c1db7..8146e3b 100644
--- a/drivers/pcmcia/m32r_cfc.h
+++ b/drivers/pcmcia/m32r_cfc.h
@@ -71,11 +71,15 @@
 
 #define CFC_IOPORT_BASE		0x1000
 
-#if !defined(CONFIG_PLAT_USRV)
+#if defined(CONFIG_PLAT_MAPPI3)
+#define CFC_ATTR_MAPBASE	0x14014000
+#define CFC_IO_MAPBASE_BYTE	0xb4012000
+#define CFC_IO_MAPBASE_WORD	0xb4002000
+#elif !defined(CONFIG_PLAT_USRV)
 #define CFC_ATTR_MAPBASE        0x0c014000
 #define CFC_IO_MAPBASE_BYTE     0xac012000
 #define CFC_IO_MAPBASE_WORD     0xac002000
-#else	/* CONFIG_PLAT_USRV */
+#else
 #define CFC_ATTR_MAPBASE	0x04014000
 #define CFC_IO_MAPBASE_BYTE	0xa4012000
 #define CFC_IO_MAPBASE_WORD	0xa4002000
diff --git a/drivers/s390/cio/blacklist.c b/drivers/s390/cio/blacklist.c
index 4a06c7d..aac83ce 100644
--- a/drivers/s390/cio/blacklist.c
+++ b/drivers/s390/cio/blacklist.c
@@ -1,7 +1,7 @@
 /*
  *  drivers/s390/cio/blacklist.c
  *   S/390 common I/O routines -- blacklisting of specific devices
- *   $Revision: 1.33 $
+ *   $Revision: 1.34 $
  *
  *    Copyright (C) 1999-2002 IBM Deutschland Entwicklung GmbH,
  *			      IBM Corporation
@@ -289,7 +289,7 @@
 	len = 0;
 	for (devno = off; /* abuse the page variable
 			   * as counter, see fs/proc/generic.c */
-	     devno <= __MAX_SUBCHANNELS && len + entry_size < count; devno++) {
+	     devno < __MAX_SUBCHANNELS && len + entry_size < count; devno++) {
 		if (!test_bit(devno, bl_dev))
 			continue;
 		len += sprintf(page + len, "0.0.%04lx", devno);
@@ -302,7 +302,7 @@
 		len += sprintf(page + len, "\n");
 	}
 
-	if (devno <= __MAX_SUBCHANNELS)
+	if (devno < __MAX_SUBCHANNELS)
 		*eof = 1;
 	*start = (char *) (devno - off); /* number of checked entries */
 	return len;
diff --git a/drivers/scsi/megaraid.c b/drivers/scsi/megaraid.c
index 80b0c40..ec81532 100644
--- a/drivers/scsi/megaraid.c
+++ b/drivers/scsi/megaraid.c
@@ -1975,7 +1975,7 @@
 static int
 megaraid_reset(Scsi_Cmnd *cmd)
 {
-	adapter = (adapter_t *)cmd->device->host->hostdata;
+	adapter_t *adapter = (adapter_t *)cmd->device->host->hostdata;
 	int rc;
 
 	spin_lock_irq(&adapter->lock);
diff --git a/drivers/serial/Kconfig b/drivers/serial/Kconfig
index 6e44b46..25fcef2 100644
--- a/drivers/serial/Kconfig
+++ b/drivers/serial/Kconfig
@@ -753,7 +753,7 @@
 
 config SERIAL_ICOM
 	tristate "IBM Multiport Serial Adapter"
-	depends on PPC_ISERIES || PPC_PSERIES
+	depends on PCI && (PPC_ISERIES || PPC_PSERIES)
 	select SERIAL_CORE
 	help
 	  This driver is for a family of multiport serial adapters
@@ -843,4 +843,13 @@
           To compile this driver as a module, choose M here: the
           module will be called jsm.
 
+config SERIAL_SGI_IOC4
+	tristate "SGI IOC4 controller serial support"
+	depends on (IA64_GENERIC || IA64_SGI_SN2) && SGI_IOC4
+	select SERIAL_CORE
+	help
+		If you have an SGI Altix with an IOC4 based Base IO card
+		and wish to use the serial ports on this card, say Y.
+		Otherwise, say N.
+
 endmenu
diff --git a/drivers/serial/Makefile b/drivers/serial/Makefile
index 81b77d7..8f1cdde 100644
--- a/drivers/serial/Makefile
+++ b/drivers/serial/Makefile
@@ -51,4 +51,4 @@
 obj-$(CONFIG_SERIAL_JSM) += jsm/
 obj-$(CONFIG_SERIAL_TXX9) += serial_txx9.o
 obj-$(CONFIG_SERIAL_VR41XX) += vr41xx_siu.o
-obj-$(CONFIG_BLK_DEV_SGIIOC4) += ioc4_serial.o
+obj-$(CONFIG_SERIAL_SGI_IOC4) += ioc4_serial.o
diff --git a/drivers/serial/cpm_uart/cpm_uart_cpm2.c b/drivers/serial/cpm_uart/cpm_uart_cpm2.c
index b422c3a..c4c8f4b 100644
--- a/drivers/serial/cpm_uart/cpm_uart_cpm2.c
+++ b/drivers/serial/cpm_uart/cpm_uart_cpm2.c
@@ -134,12 +134,21 @@
 
 void scc2_lineif(struct uart_cpm_port *pinfo)
 {
+	/*
+	 * STx GP3 uses the SCC2 secondary option pin assignment
+	 * which this driver doesn't account for in the static
+	 * pin assignments. This kind of board specific info
+	 * really has to get out of the driver so boards can
+	 * be supported in a sane fashion.
+	 */
+#ifndef CONFIG_STX_GP3
 	volatile iop_cpm2_t *io = &cpm2_immr->im_ioport;
 	io->iop_pparb |= 0x008b0000;
 	io->iop_pdirb |= 0x00880000;
 	io->iop_psorb |= 0x00880000;
 	io->iop_pdirb &= ~0x00030000;
 	io->iop_psorb &= ~0x00030000;
+#endif
 	cpm2_immr->im_cpmux.cmx_scr &= 0xff00ffff;
 	cpm2_immr->im_cpmux.cmx_scr |= 0x00090000;
 	pinfo->brg = 2;
diff --git a/drivers/serial/ioc4_serial.c b/drivers/serial/ioc4_serial.c
index ba4e13a..793c3a7 100644
--- a/drivers/serial/ioc4_serial.c
+++ b/drivers/serial/ioc4_serial.c
@@ -20,7 +20,7 @@
 #include <linux/serial_reg.h>
 #include <linux/module.h>
 #include <linux/pci.h>
-#include <linux/ioc4_common.h>
+#include <linux/ioc4.h>
 #include <linux/serial_core.h>
 
 /*
@@ -130,12 +130,19 @@
 				 IOC4_SIO_IR_S3_TX_EXPLICIT)
 
 /* Bitmasks for IOC4_OTHER_IR, IOC4_OTHER_IEC, and IOC4_OTHER_IES  */
-#define IOC4_OTHER_IR_ATA_INT           0x00000001  /* ATAPI intr pass-thru */
-#define IOC4_OTHER_IR_ATA_MEMERR        0x00000002  /* ATAPI DMA PCI error */
-#define IOC4_OTHER_IR_S0_MEMERR         0x00000004  /* Port 0 PCI error */
-#define IOC4_OTHER_IR_S1_MEMERR         0x00000008  /* Port 1 PCI error */
-#define IOC4_OTHER_IR_S2_MEMERR         0x00000010  /* Port 2 PCI error */
-#define IOC4_OTHER_IR_S3_MEMERR         0x00000020  /* Port 3 PCI error */
+#define IOC4_OTHER_IR_ATA_INT		0x00000001  /* ATAPI intr pass-thru */
+#define IOC4_OTHER_IR_ATA_MEMERR	0x00000002  /* ATAPI DMA PCI error */
+#define IOC4_OTHER_IR_S0_MEMERR		0x00000004  /* Port 0 PCI error */
+#define IOC4_OTHER_IR_S1_MEMERR		0x00000008  /* Port 1 PCI error */
+#define IOC4_OTHER_IR_S2_MEMERR		0x00000010  /* Port 2 PCI error */
+#define IOC4_OTHER_IR_S3_MEMERR		0x00000020  /* Port 3 PCI error */
+#define IOC4_OTHER_IR_KBD_INT		0x00000040  /* Keyboard/mouse */
+#define IOC4_OTHER_IR_RESERVED		0x007fff80  /* Reserved */
+#define IOC4_OTHER_IR_RT_INT		0x00800000  /* INT_OUT section output */
+#define IOC4_OTHER_IR_GEN_INT		0xff000000  /* Generic pins */
+
+#define IOC4_OTHER_IR_SER_MEMERR (IOC4_OTHER_IR_S0_MEMERR | IOC4_OTHER_IR_S1_MEMERR | \
+				  IOC4_OTHER_IR_S2_MEMERR | IOC4_OTHER_IR_S3_MEMERR)
 
 /* Bitmasks for IOC4_SIO_CR */
 #define IOC4_SIO_CR_CMD_PULSE_SHIFT              0  /* byte bus strobe shift */
@@ -274,70 +281,24 @@
 #define i4u_dlm u2.dlm
 #define i4u_fcr u3.fcr
 
-/* PCI memory space register map addressed using pci_bar0 */
-struct ioc4_memregs {
-	struct ioc4_mem {
-		/* Miscellaneous IOC4  registers */
-		uint32_t pci_err_addr_l;
-		uint32_t pci_err_addr_h;
-		uint32_t sio_ir;
-		uint32_t other_ir;
+/* Serial port registers used for DMA serial I/O */
+struct ioc4_serial {
+	uint32_t sbbr01_l;
+	uint32_t sbbr01_h;
+	uint32_t sbbr23_l;
+	uint32_t sbbr23_h;
 
-		/* These registers are read-only for general kernel code.  */
-		uint32_t sio_ies_ro;
-		uint32_t other_ies_ro;
-		uint32_t sio_iec_ro;
-		uint32_t other_iec_ro;
-		uint32_t sio_cr;
-		uint32_t misc_fill1;
-		uint32_t int_out;
-		uint32_t misc_fill2;
-		uint32_t gpcr_s;
-		uint32_t gpcr_c;
-		uint32_t gpdr;
-		uint32_t misc_fill3;
-		uint32_t gppr_0;
-		uint32_t gppr_1;
-		uint32_t gppr_2;
-		uint32_t gppr_3;
-		uint32_t gppr_4;
-		uint32_t gppr_5;
-		uint32_t gppr_6;
-		uint32_t gppr_7;
-	} ioc4_mem;
-
-	char misc_fill4[0x100 - 0x5C - 4];
-
-	/* ATA/ATAP registers */
-	uint32_t ata_notused[9];
-	char ata_fill1[0x140 - 0x120 - 4];
-	uint32_t ata_notused1[8];
-	char ata_fill2[0x200 - 0x15C - 4];
-
-	/* Keyboard and mouse registers */
-	uint32_t km_notused[5];;
-	char km_fill1[0x300 - 0x210 - 4];
-
-	/* Serial port registers used for DMA serial I/O */
-	struct ioc4_serial {
-		uint32_t sbbr01_l;
-		uint32_t sbbr01_h;
-		uint32_t sbbr23_l;
-		uint32_t sbbr23_h;
-
-		struct ioc4_serialregs port_0;
-		struct ioc4_serialregs port_1;
-		struct ioc4_serialregs port_2;
-		struct ioc4_serialregs port_3;
-		struct ioc4_uartregs uart_0;
-		struct ioc4_uartregs uart_1;
-		struct ioc4_uartregs uart_2;
-		struct ioc4_uartregs uart_3;
-	} ioc4_serial;
-};
+	struct ioc4_serialregs port_0;
+	struct ioc4_serialregs port_1;
+	struct ioc4_serialregs port_2;
+	struct ioc4_serialregs port_3;
+	struct ioc4_uartregs uart_0;
+	struct ioc4_uartregs uart_1;
+	struct ioc4_uartregs uart_2;
+	struct ioc4_uartregs uart_3;
+} ioc4_serial;
 
 /* UART clock speed */
-#define IOC4_SER_XIN_CLK        IOC4_SER_XIN_CLK_66
 #define IOC4_SER_XIN_CLK_66     66666667
 #define IOC4_SER_XIN_CLK_33     33333333
 
@@ -412,8 +373,8 @@
 					| UART_LCR_WLEN7 | UART_LCR_WLEN8)
 #define LCR_MASK_STOP_BITS	(UART_LCR_STOP)
 
-#define PENDING(_p)	(readl(&(_p)->ip_mem->sio_ir) & _p->ip_ienb)
-#define READ_SIO_IR(_p) readl(&(_p)->ip_mem->sio_ir)
+#define PENDING(_p)	(readl(&(_p)->ip_mem->sio_ir.raw) & _p->ip_ienb)
+#define READ_SIO_IR(_p) readl(&(_p)->ip_mem->sio_ir.raw)
 
 /* Default to 4k buffers */
 #ifdef IOC4_1K_BUFFERS
@@ -447,7 +408,7 @@
  */
 #define MAX_IOC4_INTR_ENTS	(8 * sizeof(uint32_t))
 struct ioc4_soft {
-	struct ioc4_mem __iomem *is_ioc4_mem_addr;
+	struct ioc4_misc_regs __iomem *is_ioc4_misc_addr;
 	struct ioc4_serial __iomem *is_ioc4_serial_addr;
 
 	/* Each interrupt type has an entry in the array */
@@ -486,7 +447,7 @@
 	struct ioc4_soft *ip_ioc4_soft;
 
 	/* pci mem addresses */
-	struct ioc4_mem __iomem *ip_mem;
+	struct ioc4_misc_regs __iomem *ip_mem;
 	struct ioc4_serial __iomem *ip_serial;
 	struct ioc4_serialregs __iomem *ip_serial_regs;
 	struct ioc4_uartregs __iomem *ip_uart_regs;
@@ -553,7 +514,7 @@
 	uint32_t intr_dma_error;
 	uint32_t intr_clear;
 	uint32_t intr_all;
-	char rs422_select_pin;
+	int rs422_select_pin;
 };
 
 static struct hooks hooks_array[IOC4_NUM_SERIAL_PORTS] = {
@@ -669,7 +630,7 @@
 static inline void
 write_ireg(struct ioc4_soft *ioc4_soft, uint32_t val, int which, int type)
 {
-	struct ioc4_mem __iomem *mem = ioc4_soft->is_ioc4_mem_addr;
+	struct ioc4_misc_regs __iomem *mem = ioc4_soft->is_ioc4_misc_addr;
 	unsigned long flags;
 
 	spin_lock_irqsave(&ioc4_soft->is_ir_lock, flags);
@@ -678,11 +639,11 @@
 	case IOC4_SIO_INTR_TYPE:
 		switch (which) {
 		case IOC4_W_IES:
-			writel(val, &mem->sio_ies_ro);
+			writel(val, &mem->sio_ies.raw);
 			break;
 
 		case IOC4_W_IEC:
-			writel(val, &mem->sio_iec_ro);
+			writel(val, &mem->sio_iec.raw);
 			break;
 		}
 		break;
@@ -690,11 +651,11 @@
 	case IOC4_OTHER_INTR_TYPE:
 		switch (which) {
 		case IOC4_W_IES:
-			writel(val, &mem->other_ies_ro);
+			writel(val, &mem->other_ies.raw);
 			break;
 
 		case IOC4_W_IEC:
-			writel(val, &mem->other_iec_ro);
+			writel(val, &mem->other_iec.raw);
 			break;
 		}
 		break;
@@ -747,7 +708,8 @@
  */
 static struct ioc4_port *get_ioc4_port(struct uart_port *the_port)
 {
-	struct ioc4_control *control = dev_get_drvdata(the_port->dev);
+	struct ioc4_driver_data *idd = dev_get_drvdata(the_port->dev);
+	struct ioc4_control *control = idd->idd_serial_data;
 	int ii;
 
 	if (control) {
@@ -782,7 +744,7 @@
 static inline uint32_t
 pending_intrs(struct ioc4_soft *soft, int type)
 {
-	struct ioc4_mem __iomem *mem = soft->is_ioc4_mem_addr;
+	struct ioc4_misc_regs __iomem *mem = soft->is_ioc4_misc_addr;
 	unsigned long flag;
 	uint32_t intrs = 0;
 
@@ -793,11 +755,11 @@
 
 	switch (type) {
 	case IOC4_SIO_INTR_TYPE:
-		intrs = readl(&mem->sio_ir) & readl(&mem->sio_ies_ro);
+		intrs = readl(&mem->sio_ir.raw) & readl(&mem->sio_ies.raw);
 		break;
 
 	case IOC4_OTHER_INTR_TYPE:
-		intrs = readl(&mem->other_ir) & readl(&mem->other_ies_ro);
+		intrs = readl(&mem->other_ir.raw) & readl(&mem->other_ies.raw);
 
 		/* Don't process any ATA interrupte */
 		intrs &= ~(IOC4_OTHER_IR_ATA_INT | IOC4_OTHER_IR_ATA_MEMERR);
@@ -826,7 +788,7 @@
 
 	/* Wait until any pending bus activity for this port has ceased */
 	do
-		sio_cr = readl(&port->ip_mem->sio_cr);
+		sio_cr = readl(&port->ip_mem->sio_cr.raw);
 	while (!(sio_cr & IOC4_SIO_CR_SIO_DIAG_IDLE));
 
 	/* Finish reset sequence */
@@ -899,7 +861,7 @@
 	write_ireg(port->ip_ioc4_soft, hooks->intr_clear,
 		       IOC4_W_IEC, IOC4_SIO_INTR_TYPE);
 	port->ip_ienb &= ~hooks->intr_clear;
-	writel(hooks->intr_clear, &port->ip_mem->sio_ir);
+	writel(hooks->intr_clear, &port->ip_mem->sio_ir.raw);
 	return 0;
 }
 
@@ -918,23 +880,23 @@
 	spin_lock_irqsave(&port->ip_lock, flags);
 
 	/* ACK the interrupt */
-	writel(hooks->intr_dma_error, &port->ip_mem->other_ir);
+	writel(hooks->intr_dma_error, &port->ip_mem->other_ir.raw);
 
-	if (readl(&port->ip_mem->pci_err_addr_l) & IOC4_PCI_ERR_ADDR_VLD) {
+	if (readl(&port->ip_mem->pci_err_addr_l.raw) & IOC4_PCI_ERR_ADDR_VLD) {
 		printk(KERN_ERR
 			"PCI error address is 0x%lx, "
 				"master is serial port %c %s\n",
 		     (((uint64_t)readl(&port->ip_mem->pci_err_addr_h)
 							 << 32)
-				| readl(&port->ip_mem->pci_err_addr_l))
+				| readl(&port->ip_mem->pci_err_addr_l.raw))
 					& IOC4_PCI_ERR_ADDR_ADDR_MSK, '1' +
-		     ((char)(readl(&port->ip_mem-> pci_err_addr_l) &
+		     ((char)(readl(&port->ip_mem->pci_err_addr_l.raw) &
 			     IOC4_PCI_ERR_ADDR_MST_NUM_MSK) >> 1),
-		     (readl(&port->ip_mem->pci_err_addr_l)
+		     (readl(&port->ip_mem->pci_err_addr_l.raw)
 				& IOC4_PCI_ERR_ADDR_MST_TYP_MSK)
 				? "RX" : "TX");
 
-		if (readl(&port->ip_mem->pci_err_addr_l)
+		if (readl(&port->ip_mem->pci_err_addr_l.raw)
 						& IOC4_PCI_ERR_ADDR_MUL_ERR) {
 			printk(KERN_ERR
 				"Multiple errors occurred\n");
@@ -1018,26 +980,26 @@
 				"other_ies = 0x%x\n",
 			       (intr_type == IOC4_SIO_INTR_TYPE) ? "sio" :
 			       "other", this_ir,
-			       readl(&soft->is_ioc4_mem_addr->sio_ir),
-			       readl(&soft->is_ioc4_mem_addr->sio_ies_ro),
-			       readl(&soft->is_ioc4_mem_addr->other_ir),
-			       readl(&soft->is_ioc4_mem_addr->other_ies_ro));
+			       readl(&soft->is_ioc4_misc_addr->sio_ir.raw),
+			       readl(&soft->is_ioc4_misc_addr->sio_ies.raw),
+			       readl(&soft->is_ioc4_misc_addr->other_ir.raw),
+			       readl(&soft->is_ioc4_misc_addr->other_ies.raw));
 		}
 	}
 #ifdef DEBUG_INTERRUPTS
 	{
-		struct ioc4_mem __iomem *mem = soft->is_ioc4_mem_addr;
+		struct ioc4_misc_regs __iomem *mem = soft->is_ioc4_misc_addr;
 		spinlock_t *lp = &soft->is_ir_lock;
 		unsigned long flag;
 
 		spin_lock_irqsave(&soft->is_ir_lock, flag);
-		printk ("%s : %d : mem 0x%p sio_ir 0x%x sio_ies_ro 0x%x "
-				"other_ir 0x%x other_ies_ro 0x%x mask 0x%x\n",
+		printk ("%s : %d : mem 0x%p sio_ir 0x%x sio_ies 0x%x "
+				"other_ir 0x%x other_ies 0x%x mask 0x%x\n",
 		     __FUNCTION__, __LINE__,
-		     (void *)mem, readl(&mem->sio_ir),
-		     readl(&mem->sio_ies_ro),
-		     readl(&mem->other_ir),
-		     readl(&mem->other_ies_ro),
+		     (void *)mem, readl(&mem->sio_ir.raw),
+		     readl(&mem->sio_ies.raw),
+		     readl(&mem->other_ir.raw),
+		     readl(&mem->other_ies.raw),
 		     IOC4_OTHER_IR_ATA_INT | IOC4_OTHER_IR_ATA_MEMERR);
 		spin_unlock_irqrestore(&soft->is_ir_lock, flag);
 	}
@@ -1049,21 +1011,20 @@
  * ioc4_attach_local - Device initialization.
  *			Called at *_attach() time for each
  *			IOC4 with serial ports in the system.
- * @control: ioc4_control ptr
- * @pdev: PCI handle for this device
- * @soft: soft struct for this device
- * @ioc4: ioc4 mem space
+ * @idd: Master module data for this IOC4
  */
-static int inline ioc4_attach_local(struct pci_dev *pdev,
-			struct ioc4_control *control,
-			struct ioc4_soft *soft, void __iomem *ioc4_mem,
-			void __iomem *ioc4_serial)
+static int inline ioc4_attach_local(struct ioc4_driver_data *idd)
 {
 	struct ioc4_port *port;
 	struct ioc4_port *ports[IOC4_NUM_SERIAL_PORTS];
 	int port_number;
 	uint16_t ioc4_revid_min = 62;
 	uint16_t ioc4_revid;
+	struct pci_dev *pdev = idd->idd_pdev;
+	struct ioc4_control* control = idd->idd_serial_data;
+	struct ioc4_soft *soft = control->ic_soft;
+	void __iomem *ioc4_misc = idd->idd_misc_regs;
+	void __iomem *ioc4_serial = soft->is_ioc4_serial_addr;
 
 	/* IOC4 firmware must be at least rev 62 */
 	pci_read_config_word(pdev, PCI_COMMAND_SPECIAL, &ioc4_revid);
@@ -1076,7 +1037,7 @@
 				ioc4_revid, ioc4_revid_min);
 		return -EPERM;
 	}
-	BUG_ON(ioc4_mem == NULL);
+	BUG_ON(ioc4_misc == NULL);
 	BUG_ON(ioc4_serial == NULL);
 
 	/* Create port structures for each port */
@@ -1100,10 +1061,18 @@
 		port->ip_ioc4_soft = soft;
 		port->ip_pdev = pdev;
 		port->ip_ienb = 0;
-		port->ip_pci_bus_speed = IOC4_SER_XIN_CLK;
+		/* Use baud rate calculations based on detected PCI
+		 * bus speed.  Simply test whether the PCI clock is
+		 * running closer to 66MHz or 33MHz.
+		 */
+		if (idd->count_period/IOC4_EXTINT_COUNT_DIVISOR < 20) {
+			port->ip_pci_bus_speed = IOC4_SER_XIN_CLK_66;
+		} else {
+			port->ip_pci_bus_speed = IOC4_SER_XIN_CLK_33;
+		}
 		port->ip_baud = 9600;
 		port->ip_control = control;
-		port->ip_mem = ioc4_mem;
+		port->ip_mem = ioc4_misc;
 		port->ip_serial = ioc4_serial;
 
 		/* point to the right hook */
@@ -1604,14 +1573,12 @@
 	switch (proto) {
 	case PROTO_RS232:
 		/* Clear the appropriate GIO pin */
-		writel(0, (&port->ip_mem->gppr_0 +
-				  hooks->rs422_select_pin));
+		writel(0, (&port->ip_mem->gppr[hooks->rs422_select_pin].raw));
 		break;
 
 	case PROTO_RS422:
 		/* Set the appropriate GIO pin */
-		writel(1, (&port->ip_mem->gppr_0 +
-				  hooks->rs422_select_pin));
+		writel(1, (&port->ip_mem->gppr[hooks->rs422_select_pin].raw));
 		break;
 
 	default:
@@ -1885,7 +1852,7 @@
 		if (sio_ir & hooks->intr_delta_dcd) {
 			/* ACK the interrupt */
 			writel(hooks->intr_delta_dcd,
-				&port->ip_mem->sio_ir);
+				&port->ip_mem->sio_ir.raw);
 
 			shadow = readl(&port->ip_serial_regs->shadow);
 
@@ -1907,7 +1874,7 @@
 		if (sio_ir & hooks->intr_delta_cts) {
 			/* ACK the interrupt */
 			writel(hooks->intr_delta_cts,
-					&port->ip_mem->sio_ir);
+					&port->ip_mem->sio_ir.raw);
 
 			shadow = readl(&port->ip_serial_regs->shadow);
 
@@ -1928,7 +1895,7 @@
 		if (sio_ir & hooks->intr_rx_timer) {
 			/* ACK the interrupt */
 			writel(hooks->intr_rx_timer,
-				&port->ip_mem->sio_ir);
+				&port->ip_mem->sio_ir.raw);
 
 			if ((port->ip_notify & N_DATA_READY)
 					&& (port->ip_port)) {
@@ -1974,7 +1941,7 @@
 
 			/* ACK the interrupt */
 			writel(hooks->intr_tx_explicit,
-					&port->ip_mem->sio_ir);
+					&port->ip_mem->sio_ir.raw);
 
 			if (port->ip_notify & N_OUTPUT_LOWAT)
 				ioc4_cb_output_lowat(port);
@@ -2634,7 +2601,8 @@
 {
 	struct ioc4_port *port;
 	struct uart_port *the_port;
-	struct ioc4_control *control = pci_get_drvdata(pdev);
+	struct ioc4_driver_data *idd = pci_get_drvdata(pdev);
+	struct ioc4_control *control = idd->idd_serial_data;
 	int ii;
 
 	DPRINT_CONFIG(("%s: attach pdev 0x%p - control 0x%p\n",
@@ -2680,55 +2648,29 @@
 
 /**
  * ioc4_serial_attach_one - register attach function
- *		called per card found from ioc4_serial_detect as part
- *		of module_init().
- * @pdev: handle for this card
- * @pci_id: pci id for this card
+ *		called per card found from IOC4 master module.
+ * @idd: Master module data for this IOC4
  */
 int
-ioc4_serial_attach_one(struct pci_dev *pdev, const struct pci_device_id *pci_id)
+ioc4_serial_attach_one(struct ioc4_driver_data *idd)
 {
-	struct ioc4_mem __iomem *mem;
-	unsigned long tmp_addr, tmp_addr1;
+	unsigned long tmp_addr1;
 	struct ioc4_serial __iomem *serial;
 	struct ioc4_soft *soft;
 	struct ioc4_control *control;
-	int tmp, ret = 0;
+	int ret = 0;
 
 
-	DPRINT_CONFIG(("%s (0x%p, 0x%p)\n", __FUNCTION__, pdev, pci_id));
-
-	/* Map in the ioc4 memory */
-	tmp_addr = pci_resource_start(pdev, 0);
-	if (!tmp_addr) {
-		printk(KERN_WARNING
-			 "ioc4 (%p) : unable to get PIO mapping for "
-				"MEM space\n", (void *)pdev);
-		return -ENODEV;
-	}
-	if (!request_region(tmp_addr, sizeof(struct ioc4_mem), "sioc4_mem")) {
-		printk(KERN_ALERT
-			"ioc4 (%p): unable to get request region for "
-			"MEM space\n", (void *)pdev);
-		return -ENODEV;
-	}
-	mem = ioremap(tmp_addr, sizeof(struct ioc4_mem));
-	if (!mem) {
-		printk(KERN_WARNING
-			 "ioc4 (%p) : unable to remap ioc4 memory\n",
-				(void *)pdev);
-		ret = -ENODEV;
-		goto out1;
-	}
+	DPRINT_CONFIG(("%s (0x%p, 0x%p)\n", __FUNCTION__, idd->idd_pdev, idd->idd_pci_id));
 
 	/* request serial registers */
-	tmp_addr1 = pci_resource_start(pdev, 0) + IOC4_SERIAL_OFFSET;
+	tmp_addr1 = idd->idd_bar0 + IOC4_SERIAL_OFFSET;
 
 	if (!request_region(tmp_addr1, sizeof(struct ioc4_serial),
 					"sioc4_uart")) {
 		printk(KERN_WARNING
 			"ioc4 (%p): unable to get request region for "
-				"uart space\n", (void *)pdev);
+				"uart space\n", (void *)idd->idd_pdev);
 		ret = -ENODEV;
 		goto out1;
 	}
@@ -2736,12 +2678,12 @@
 	if (!serial) {
 		printk(KERN_WARNING
 			 "ioc4 (%p) : unable to remap ioc4 serial register\n",
-				(void *)pdev);
+				(void *)idd->idd_pdev);
 		ret = -ENODEV;
 		goto out2;
 	}
 	DPRINT_CONFIG(("%s : mem 0x%p, serial 0x%p\n",
-				__FUNCTION__, (void *)mem, (void *)serial));
+				__FUNCTION__, (void *)idd->idd_misc_regs, (void *)serial));
 
 	/* Get memory for the new card */
 	control = kmalloc(sizeof(struct ioc4_control) * IOC4_NUM_SERIAL_PORTS,
@@ -2754,59 +2696,56 @@
 		goto out2;
 	}
 	memset(control, 0, sizeof(struct ioc4_control));
-	pci_set_drvdata(pdev, control);
+	idd->idd_serial_data = control;
 
 	/* Allocate the soft structure */
 	soft = kmalloc(sizeof(struct ioc4_soft), GFP_KERNEL);
 	if (!soft) {
 		printk(KERN_WARNING
 		       "ioc4 (%p): unable to get memory for the soft struct\n",
-		       (void *)pdev);
+		       (void *)idd->idd_pdev);
 		ret = -ENOMEM;
 		goto out3;
 	}
 	memset(soft, 0, sizeof(struct ioc4_soft));
 
 	spin_lock_init(&soft->is_ir_lock);
-	soft->is_ioc4_mem_addr = mem;
+	soft->is_ioc4_misc_addr = idd->idd_misc_regs;
 	soft->is_ioc4_serial_addr = serial;
 
 	/* Init the IOC4 */
-	pci_read_config_dword(pdev, PCI_COMMAND, &tmp);
-	pci_write_config_dword(pdev, PCI_COMMAND,
-			       tmp | PCI_COMMAND_PARITY | PCI_COMMAND_SERR);
-
-	writel(0xf << IOC4_SIO_CR_CMD_PULSE_SHIFT, &mem->sio_cr);
+	writel(0xf << IOC4_SIO_CR_CMD_PULSE_SHIFT,
+	       &idd->idd_misc_regs->sio_cr.raw);
 
 	/* Enable serial port mode select generic PIO pins as outputs */
 	writel(IOC4_GPCR_UART0_MODESEL | IOC4_GPCR_UART1_MODESEL
 		| IOC4_GPCR_UART2_MODESEL | IOC4_GPCR_UART3_MODESEL,
-		&mem->gpcr_s);
+		&idd->idd_misc_regs->gpcr_s.raw);
 
-	/* Clear and disable all interrupts */
+	/* Clear and disable all serial interrupts */
 	write_ireg(soft, ~0, IOC4_W_IEC, IOC4_SIO_INTR_TYPE);
-	writel(~0, &mem->sio_ir);
-	write_ireg(soft, ~(IOC4_OTHER_IR_ATA_INT | IOC4_OTHER_IR_ATA_MEMERR),
-			IOC4_W_IEC, IOC4_OTHER_INTR_TYPE);
-	writel(~(IOC4_OTHER_IR_ATA_MEMERR | IOC4_OTHER_IR_ATA_MEMERR),
-					&mem->other_ir);
+	writel(~0, &idd->idd_misc_regs->sio_ir.raw);
+	write_ireg(soft, IOC4_OTHER_IR_SER_MEMERR, IOC4_W_IEC,
+		   IOC4_OTHER_INTR_TYPE);
+	writel(IOC4_OTHER_IR_SER_MEMERR, &idd->idd_misc_regs->other_ir.raw);
 	control->ic_soft = soft;
-	if (!request_irq(pdev->irq, ioc4_intr, SA_SHIRQ,
+
+	/* Hook up interrupt handler */
+	if (!request_irq(idd->idd_pdev->irq, ioc4_intr, SA_SHIRQ,
 				"sgi-ioc4serial", (void *)soft)) {
-		control->ic_irq = pdev->irq;
+		control->ic_irq = idd->idd_pdev->irq;
 	} else {
 		printk(KERN_WARNING
 		    "%s : request_irq fails for IRQ 0x%x\n ",
-			__FUNCTION__, pdev->irq);
+			__FUNCTION__, idd->idd_pdev->irq);
 	}
-	if ((ret = ioc4_attach_local(pdev, control, soft,
-				soft->is_ioc4_mem_addr,
-				soft->is_ioc4_serial_addr)))
+	ret = ioc4_attach_local(idd);
+	if (ret)
 		goto out4;
 
 	/* register port with the serial core */
 
-	if ((ret = ioc4_serial_core_attach(pdev)))
+	if ((ret = ioc4_serial_core_attach(idd->idd_pdev)))
 		goto out4;
 
 	return ret;
@@ -2819,7 +2758,6 @@
 out2:
 	release_region(tmp_addr1, sizeof(struct ioc4_serial));
 out1:
-	release_region(tmp_addr, sizeof(struct ioc4_mem));
 
 	return ret;
 }
@@ -2828,11 +2766,10 @@
 /**
  * ioc4_serial_remove_one - detach function
  *
- * @pdev: handle for this card
+ * @idd: IOC4 master module data for this IOC4
  */
 
-#if 0
-void ioc4_serial_remove_one(struct pci_dev *pdev)
+int ioc4_serial_remove_one(struct ioc4_driver_data *idd)
 {
 	int ii;
 	struct ioc4_control *control;
@@ -2840,7 +2777,7 @@
 	struct ioc4_port *port;
 	struct ioc4_soft *soft;
 
-	control = pci_get_drvdata(pdev);
+	control = idd->idd_serial_data;
 
 	for (ii = 0; ii < IOC4_NUM_SERIAL_PORTS; ii++) {
 		the_port = &control->ic_port[ii].icp_uart_port;
@@ -2867,10 +2804,17 @@
 		kfree(soft);
 	}
 	kfree(control);
-	pci_set_drvdata(pdev, NULL);
-	uart_unregister_driver(&ioc4_uart);
+	idd->idd_serial_data = NULL;
+
+	return 0;
 }
-#endif
+
+static struct ioc4_submodule ioc4_serial_submodule = {
+	.is_name = "IOC4_serial",
+	.is_owner = THIS_MODULE,
+	.is_probe = ioc4_serial_attach_one,
+	.is_remove = ioc4_serial_remove_one,
+};
 
 /**
  * ioc4_serial_init - module init
@@ -2886,12 +2830,20 @@
 			__FUNCTION__);
 		return ret;
 	}
-	return 0;
+
+	/* register with IOC4 main module */
+	return ioc4_register_submodule(&ioc4_serial_submodule);
 }
 
+static void __devexit ioc4_serial_exit(void)
+{
+	ioc4_unregister_submodule(&ioc4_serial_submodule);
+	uart_unregister_driver(&ioc4_uart);
+}
+
+module_init(ioc4_serial_init);
+module_exit(ioc4_serial_exit);
+
 MODULE_AUTHOR("Pat Gefre - Silicon Graphics Inc. (SGI) <pfg@sgi.com>");
 MODULE_DESCRIPTION("Serial PCI driver module for SGI IOC4 Base-IO Card");
 MODULE_LICENSE("GPL");
-
-EXPORT_SYMBOL(ioc4_serial_init);
-EXPORT_SYMBOL(ioc4_serial_attach_one);
diff --git a/drivers/sn/Kconfig b/drivers/sn/Kconfig
new file mode 100644
index 0000000..13b8d24
--- /dev/null
+++ b/drivers/sn/Kconfig
@@ -0,0 +1,20 @@
+#
+# Miscellaneous SN-specific devices
+#
+
+menu "SN Devices"
+
+config SGI_IOC4
+	tristate "SGI IOC4 Base IO support"
+	depends on (IA64_GENERIC || IA64_SGI_SN2) && MMTIMER
+	default m
+	---help---
+	This option enables basic support for the SGI IOC4-based Base IO
+	controller card.  This option does not enable any specific
+	functions on such a card, but provides necessary infrastructure
+	for other drivers to utilize.
+
+	If you have an SGI Altix with an IOC4-based
+	I/O controller say Y.  Otherwise say N.
+
+endmenu
diff --git a/drivers/sn/Makefile b/drivers/sn/Makefile
index 631e549..c2a2841 100644
--- a/drivers/sn/Makefile
+++ b/drivers/sn/Makefile
@@ -3,4 +3,4 @@
 #
 #
 
-obj-$(CONFIG_BLK_DEV_SGIIOC4) += ioc4.o
+obj-$(CONFIG_SGI_IOC4) += ioc4.o
diff --git a/drivers/sn/ioc4.c b/drivers/sn/ioc4.c
index d9e4ee2..ea75b3d 100644
--- a/drivers/sn/ioc4.c
+++ b/drivers/sn/ioc4.c
@@ -6,60 +6,422 @@
  * Copyright (C) 2005 Silicon Graphics, Inc.  All Rights Reserved.
  */
 
-/*
- * This file contains a shim driver for the IOC4 IDE and serial drivers.
+/* This file contains the master driver module for use by SGI IOC4 subdrivers.
+ *
+ * It allocates any resources shared between multiple subdevices, and
+ * provides accessor functions (where needed) and the like for those
+ * resources.  It also provides a mechanism for the subdevice modules
+ * to support loading and unloading.
+ *
+ * Non-shared resources (e.g. external interrupt A_INT_OUT register page
+ * alias, serial port and UART registers) are handled by the subdevice
+ * modules themselves.
+ *
+ * This is all necessary because IOC4 is not implemented as a multi-function
+ * PCI device, but an amalgamation of disparate registers for several
+ * types of device (ATA, serial, external interrupts).  The normal
+ * resource management in the kernel doesn't have quite the right interfaces
+ * to handle this situation (e.g. multiple modules can't claim the same
+ * PCI ID), thus this IOC4 master module.
  */
 
 #include <linux/errno.h>
 #include <linux/module.h>
 #include <linux/pci.h>
-#include <linux/ioc4_common.h>
-#include <linux/ide.h>
+#include <linux/ioc4.h>
+#include <linux/mmtimer.h>
+#include <linux/rtc.h>
+#include <linux/rwsem.h>
+#include <asm/sn/addrs.h>
+#include <asm/sn/clksupport.h>
+#include <asm/sn/shub_mmr.h>
 
+/***************
+ * Definitions *
+ ***************/
 
-static int __devinit
-ioc4_probe_one(struct pci_dev *pdev, const struct pci_device_id *pci_id)
+/* Tweakable values */
+
+/* PCI bus speed detection/calibration */
+#define IOC4_CALIBRATE_COUNT 63	/* Calibration cycle period */
+#define IOC4_CALIBRATE_CYCLES 256	/* Average over this many cycles */
+#define IOC4_CALIBRATE_DISCARD 2	/* Discard first few cycles */
+#define IOC4_CALIBRATE_LOW_MHZ 25	/* Lower bound on bus speed sanity */
+#define IOC4_CALIBRATE_HIGH_MHZ 75	/* Upper bound on bus speed sanity */
+#define IOC4_CALIBRATE_DEFAULT_MHZ 66	/* Assumed if sanity check fails */
+
+/************************
+ * Submodule management *
+ ************************/
+
+static LIST_HEAD(ioc4_devices);
+static DECLARE_RWSEM(ioc4_devices_rwsem);
+
+static LIST_HEAD(ioc4_submodules);
+static DECLARE_RWSEM(ioc4_submodules_rwsem);
+
+/* Register an IOC4 submodule */
+int
+ioc4_register_submodule(struct ioc4_submodule *is)
 {
+	struct ioc4_driver_data *idd;
+
+	down_write(&ioc4_submodules_rwsem);
+	list_add(&is->is_list, &ioc4_submodules);
+	up_write(&ioc4_submodules_rwsem);
+
+	/* Initialize submodule for each IOC4 */
+	if (!is->is_probe)
+		return 0;
+
+	down_read(&ioc4_devices_rwsem);
+	list_for_each_entry(idd, &ioc4_devices, idd_list) {
+		if (is->is_probe(idd)) {
+			printk(KERN_WARNING
+			       "%s: IOC4 submodule %s probe failed "
+			       "for pci_dev %s",
+			       __FUNCTION__, module_name(is->is_owner),
+			       pci_name(idd->idd_pdev));
+		}
+	}
+	up_read(&ioc4_devices_rwsem);
+
+	return 0;
+}
+
+/* Unregister an IOC4 submodule */
+void
+ioc4_unregister_submodule(struct ioc4_submodule *is)
+{
+	struct ioc4_driver_data *idd;
+
+	down_write(&ioc4_submodules_rwsem);
+	list_del(&is->is_list);
+	up_write(&ioc4_submodules_rwsem);
+
+	/* Remove submodule for each IOC4 */
+	if (!is->is_remove)
+		return;
+
+	down_read(&ioc4_devices_rwsem);
+	list_for_each_entry(idd, &ioc4_devices, idd_list) {
+		if (is->is_remove(idd)) {
+			printk(KERN_WARNING
+			       "%s: IOC4 submodule %s remove failed "
+			       "for pci_dev %s.\n",
+			       __FUNCTION__, module_name(is->is_owner),
+			       pci_name(idd->idd_pdev));
+		}
+	}
+	up_read(&ioc4_devices_rwsem);
+}
+
+/*********************
+ * Device management *
+ *********************/
+
+#define IOC4_CALIBRATE_LOW_LIMIT \
+	(1000*IOC4_EXTINT_COUNT_DIVISOR/IOC4_CALIBRATE_LOW_MHZ)
+#define IOC4_CALIBRATE_HIGH_LIMIT \
+	(1000*IOC4_EXTINT_COUNT_DIVISOR/IOC4_CALIBRATE_HIGH_MHZ)
+#define IOC4_CALIBRATE_DEFAULT \
+	(1000*IOC4_EXTINT_COUNT_DIVISOR/IOC4_CALIBRATE_DEFAULT_MHZ)
+
+#define IOC4_CALIBRATE_END \
+	(IOC4_CALIBRATE_CYCLES + IOC4_CALIBRATE_DISCARD)
+
+#define IOC4_INT_OUT_MODE_TOGGLE 0x7	/* Toggle INT_OUT every COUNT+1 ticks */
+
+/* Determines external interrupt output clock period of the PCI bus an
+ * IOC4 is attached to.  This value can be used to determine the PCI
+ * bus speed.
+ *
+ * IOC4 has a design feature that various internal timers are derived from
+ * the PCI bus clock.  This causes IOC4 device drivers to need to take the
+ * bus speed into account when setting various register values (e.g. INT_OUT
+ * register COUNT field, UART divisors, etc).  Since this information is
+ * needed by several subdrivers, it is determined by the main IOC4 driver,
+ * even though the following code utilizes external interrupt registers
+ * to perform the speed calculation.
+ */
+static void
+ioc4_clock_calibrate(struct ioc4_driver_data *idd)
+{
+	extern unsigned long sn_rtc_cycles_per_second;
+	union ioc4_int_out int_out;
+	union ioc4_gpcr gpcr;
+	unsigned int state, last_state = 1;
+	uint64_t start = 0, end, period;
+	unsigned int count = 0;
+
+	/* Enable output */
+	gpcr.raw = 0;
+	gpcr.fields.dir = IOC4_GPCR_DIR_0;
+	gpcr.fields.int_out_en = 1;
+	writel(gpcr.raw, &idd->idd_misc_regs->gpcr_s.raw);
+
+	/* Reset to power-on state */
+	writel(0, &idd->idd_misc_regs->int_out.raw);
+	mmiowb();
+
+	printk(KERN_INFO
+	       "%s: Calibrating PCI bus speed "
+	       "for pci_dev %s ... ", __FUNCTION__, pci_name(idd->idd_pdev));
+	/* Set up square wave */
+	int_out.raw = 0;
+	int_out.fields.count = IOC4_CALIBRATE_COUNT;
+	int_out.fields.mode = IOC4_INT_OUT_MODE_TOGGLE;
+	int_out.fields.diag = 0;
+	writel(int_out.raw, &idd->idd_misc_regs->int_out.raw);
+	mmiowb();
+
+	/* Check square wave period averaged over some number of cycles */
+	do {
+		int_out.raw = readl(&idd->idd_misc_regs->int_out.raw);
+		state = int_out.fields.int_out;
+		if (!last_state && state) {
+			count++;
+			if (count == IOC4_CALIBRATE_END) {
+				end = rtc_time();
+				break;
+			} else if (count == IOC4_CALIBRATE_DISCARD)
+				start = rtc_time();
+		}
+		last_state = state;
+	} while (1);
+
+	/* Calculation rearranged to preserve intermediate precision.
+	 * Logically:
+	 * 1. "end - start" gives us number of RTC cycles over all the
+	 *    square wave cycles measured.
+	 * 2. Divide by number of square wave cycles to get number of
+	 *    RTC cycles per square wave cycle.
+	 * 3. Divide by 2*(int_out.fields.count+1), which is the formula
+	 *    by which the IOC4 generates the square wave, to get the
+	 *    number of RTC cycles per IOC4 INT_OUT count.
+	 * 4. Divide by sn_rtc_cycles_per_second to get seconds per
+	 *    count.
+	 * 5. Multiply by 1E9 to get nanoseconds per count.
+	 */
+	period = ((end - start) * 1000000000) /
+	    (IOC4_CALIBRATE_CYCLES * 2 * (IOC4_CALIBRATE_COUNT + 1)
+	     * sn_rtc_cycles_per_second);
+
+	/* Bounds check the result. */
+	if (period > IOC4_CALIBRATE_LOW_LIMIT ||
+	    period < IOC4_CALIBRATE_HIGH_LIMIT) {
+		printk("failed. Assuming PCI clock ticks are %d ns.\n",
+		       IOC4_CALIBRATE_DEFAULT / IOC4_EXTINT_COUNT_DIVISOR);
+		period = IOC4_CALIBRATE_DEFAULT;
+	} else {
+		printk("succeeded. PCI clock ticks are %ld ns.\n",
+		       period / IOC4_EXTINT_COUNT_DIVISOR);
+	}
+
+	/* Remember results.  We store the extint clock period rather
+	 * than the PCI clock period so that greater precision is
+	 * retained.  Divide by IOC4_EXTINT_COUNT_DIVISOR to get
+	 * PCI clock period.
+	 */
+	idd->count_period = period;
+}
+
+/* Adds a new instance of an IOC4 card */
+static int
+ioc4_probe(struct pci_dev *pdev, const struct pci_device_id *pci_id)
+{
+	struct ioc4_driver_data *idd;
+	struct ioc4_submodule *is;
+	uint32_t pcmd;
 	int ret;
 
+	/* Enable IOC4 and take ownership of it */
 	if ((ret = pci_enable_device(pdev))) {
 		printk(KERN_WARNING
-			 "%s: Failed to enable device with "
-				"pci_dev 0x%p... returning\n",
-				__FUNCTION__, (void *)pdev);
-		return ret;
+		       "%s: Failed to enable IOC4 device for pci_dev %s.\n",
+		       __FUNCTION__, pci_name(pdev));
+		goto out;
 	}
 	pci_set_master(pdev);
 
-	/* attach each sub-device */
-	ret = ioc4_ide_attach_one(pdev, pci_id);
-	if (ret)
-		return ret;
-	return ioc4_serial_attach_one(pdev, pci_id);
+	/* Set up per-IOC4 data */
+	idd = kmalloc(sizeof(struct ioc4_driver_data), GFP_KERNEL);
+	if (!idd) {
+		printk(KERN_WARNING
+		       "%s: Failed to allocate IOC4 data for pci_dev %s.\n",
+		       __FUNCTION__, pci_name(pdev));
+		ret = -ENODEV;
+		goto out_idd;
+	}
+	idd->idd_pdev = pdev;
+	idd->idd_pci_id = pci_id;
+
+	/* Map IOC4 misc registers.  These are shared between subdevices
+	 * so the main IOC4 module manages them.
+	 */
+	idd->idd_bar0 = pci_resource_start(idd->idd_pdev, 0);
+	if (!idd->idd_bar0) {
+		printk(KERN_WARNING
+		       "%s: Unable to find IOC4 misc resource "
+		       "for pci_dev %s.\n",
+		       __FUNCTION__, pci_name(idd->idd_pdev));
+		ret = -ENODEV;
+		goto out_pci;
+	}
+	if (!request_region(idd->idd_bar0, sizeof(struct ioc4_misc_regs),
+			    "ioc4_misc")) {
+		printk(KERN_WARNING
+		       "%s: Unable to request IOC4 misc region "
+		       "for pci_dev %s.\n",
+		       __FUNCTION__, pci_name(idd->idd_pdev));
+		ret = -ENODEV;
+		goto out_pci;
+	}
+	idd->idd_misc_regs = ioremap(idd->idd_bar0,
+				     sizeof(struct ioc4_misc_regs));
+	if (!idd->idd_misc_regs) {
+		printk(KERN_WARNING
+		       "%s: Unable to remap IOC4 misc region "
+		       "for pci_dev %s.\n",
+		       __FUNCTION__, pci_name(idd->idd_pdev));
+		ret = -ENODEV;
+		goto out_misc_region;
+	}
+
+	/* Failsafe portion of per-IOC4 initialization */
+
+	/* Initialize IOC4 */
+	pci_read_config_dword(idd->idd_pdev, PCI_COMMAND, &pcmd);
+	pci_write_config_dword(idd->idd_pdev, PCI_COMMAND,
+			       pcmd | PCI_COMMAND_PARITY | PCI_COMMAND_SERR);
+
+	/* Determine PCI clock */
+	ioc4_clock_calibrate(idd);
+
+	/* Disable/clear all interrupts.  Need to do this here lest
+	 * one submodule request the shared IOC4 IRQ, but interrupt
+	 * is generated by a different subdevice.
+	 */
+	/* Disable */
+	writel(~0, &idd->idd_misc_regs->other_iec.raw);
+	writel(~0, &idd->idd_misc_regs->sio_iec);
+	/* Clear (i.e. acknowledge) */
+	writel(~0, &idd->idd_misc_regs->other_ir.raw);
+	writel(~0, &idd->idd_misc_regs->sio_ir);
+
+	/* Track PCI-device specific data */
+	idd->idd_serial_data = NULL;
+	pci_set_drvdata(idd->idd_pdev, idd);
+	down_write(&ioc4_devices_rwsem);
+	list_add(&idd->idd_list, &ioc4_devices);
+	up_write(&ioc4_devices_rwsem);
+
+	/* Add this IOC4 to all submodules */
+	down_read(&ioc4_submodules_rwsem);
+	list_for_each_entry(is, &ioc4_submodules, is_list) {
+		if (is->is_probe && is->is_probe(idd)) {
+			printk(KERN_WARNING
+			       "%s: IOC4 submodule 0x%s probe failed "
+			       "for pci_dev %s.\n",
+			       __FUNCTION__, module_name(is->is_owner),
+			       pci_name(idd->idd_pdev));
+		}
+	}
+	up_read(&ioc4_submodules_rwsem);
+
+	return 0;
+
+out_misc_region:
+	release_region(idd->idd_bar0, sizeof(struct ioc4_misc_regs));
+out_pci:
+	kfree(idd);
+out_idd:
+	pci_disable_device(pdev);
+out:
+	return ret;
 }
 
-/* pci device struct */
-static struct pci_device_id ioc4_s_id_table[] = {
+/* Removes a particular instance of an IOC4 card. */
+static void
+ioc4_remove(struct pci_dev *pdev)
+{
+	struct ioc4_submodule *is;
+	struct ioc4_driver_data *idd;
+
+	idd = pci_get_drvdata(pdev);
+
+	/* Remove this IOC4 from all submodules */
+	down_read(&ioc4_submodules_rwsem);
+	list_for_each_entry(is, &ioc4_submodules, is_list) {
+		if (is->is_remove && is->is_remove(idd)) {
+			printk(KERN_WARNING
+			       "%s: IOC4 submodule 0x%s remove failed "
+			       "for pci_dev %s.\n",
+			       __FUNCTION__, module_name(is->is_owner),
+			       pci_name(idd->idd_pdev));
+		}
+	}
+	up_read(&ioc4_submodules_rwsem);
+
+	/* Release resources */
+	iounmap(idd->idd_misc_regs);
+	if (!idd->idd_bar0) {
+		printk(KERN_WARNING
+		       "%s: Unable to get IOC4 misc mapping for pci_dev %s. "
+		       "Device removal may be incomplete.\n",
+		       __FUNCTION__, pci_name(idd->idd_pdev));
+	}
+	release_region(idd->idd_bar0, sizeof(struct ioc4_misc_regs));
+
+	/* Disable IOC4 and relinquish */
+	pci_disable_device(pdev);
+
+	/* Remove and free driver data */
+	down_write(&ioc4_devices_rwsem);
+	list_del(&idd->idd_list);
+	up_write(&ioc4_devices_rwsem);
+	kfree(idd);
+}
+
+static struct pci_device_id ioc4_id_table[] = {
 	{PCI_VENDOR_ID_SGI, PCI_DEVICE_ID_SGI_IOC4, PCI_ANY_ID,
 	 PCI_ANY_ID, 0x0b4000, 0xFFFFFF},
 	{0}
 };
-MODULE_DEVICE_TABLE(pci, ioc4_s_id_table);
 
-static struct pci_driver __devinitdata ioc4_s_driver = {
-	.name	= "IOC4",
-	.id_table = ioc4_s_id_table,
-	.probe	= ioc4_probe_one,
+static struct pci_driver __devinitdata ioc4_driver = {
+	.name = "IOC4",
+	.id_table = ioc4_id_table,
+	.probe = ioc4_probe,
+	.remove = ioc4_remove,
 };
 
-static int __devinit ioc4_detect(void)
+MODULE_DEVICE_TABLE(pci, ioc4_id_table);
+
+/*********************
+ * Module management *
+ *********************/
+
+/* Module load */
+static int __devinit
+ioc4_init(void)
 {
-	ioc4_serial_init();
-
-	return pci_register_driver(&ioc4_s_driver);
+	return pci_register_driver(&ioc4_driver);
 }
-module_init(ioc4_detect);
 
-MODULE_AUTHOR("Pat Gefre - Silicon Graphics Inc. (SGI) <pfg@sgi.com>");
-MODULE_DESCRIPTION("PCI driver module for SGI IOC4 Base-IO Card");
+/* Module unload */
+static void __devexit
+ioc4_exit(void)
+{
+	pci_unregister_driver(&ioc4_driver);
+}
+
+module_init(ioc4_init);
+module_exit(ioc4_exit);
+
+MODULE_AUTHOR("Brent Casavant - Silicon Graphics, Inc. <bcasavan@sgi.com>");
+MODULE_DESCRIPTION("PCI driver master module for SGI IOC4 Base-IO Card");
 MODULE_LICENSE("GPL");
+
+EXPORT_SYMBOL(ioc4_register_submodule);
+EXPORT_SYMBOL(ioc4_unregister_submodule);
diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig
index 6be8fbe..04d3120 100644
--- a/drivers/video/Kconfig
+++ b/drivers/video/Kconfig
@@ -322,6 +322,22 @@
 	  This is the frame buffer device driver for the Amiga FrameMaster
 	  card from BSC (exhibited 1992 but not shipped as a CBM product).
 
+config FB_ARC
+	tristate "Arc Monochrome LCD board support"
+	depends on FB && X86
+	select FB_CFB_FILLRECT
+	select FB_CFB_COPYAREA
+	select FB_CFB_IMAGEBLIT
+	select FB_SOFT_CURSOR
+	help
+	  This enables support for the Arc Monochrome LCD board. The board
+	  is based on the KS-108 lcd controller and is typically a matrix
+	  of 2*n chips. This driver was tested with a 128x64 panel. This
+	  driver supports it for use with x86 SBCs through a 16 bit GPIO
+	  interface (8 bit data, 8 bit control). If you anticpate using
+	  this driver, say Y or M; otherwise say N. You must specify the
+	  GPIO IO address to be used for setting control and data.
+
 config FB_ATARI
 	bool "Atari native chipset support"
 	depends on (FB = y) && ATARI && BROKEN
diff --git a/drivers/video/Makefile b/drivers/video/Makefile
index bd8dc0f..b018df4 100644
--- a/drivers/video/Makefile
+++ b/drivers/video/Makefile
@@ -21,6 +21,7 @@
 # Hardware specific drivers go first
 obj-$(CONFIG_FB_RETINAZ3)         += retz3fb.o
 obj-$(CONFIG_FB_AMIGA)            += amifb.o c2p.o
+obj-$(CONFIG_FB_ARC)              += arcfb.o
 obj-$(CONFIG_FB_CLPS711X)         += clps711xfb.o
 obj-$(CONFIG_FB_CYBER)            += cyberfb.o
 obj-$(CONFIG_FB_CYBER2000)        += cyber2000fb.o
diff --git a/drivers/video/arcfb.c b/drivers/video/arcfb.c
new file mode 100644
index 0000000..d28457e
--- /dev/null
+++ b/drivers/video/arcfb.c
@@ -0,0 +1,684 @@
+/*
+ * linux/drivers/video/arcfb.c -- FB driver for Arc monochrome LCD board
+ *
+ * Copyright (C) 2005, Jaya Kumar <jayalk@intworks.biz>
+ * http://www.intworks.biz/arclcd
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file COPYING in the main directory of this archive for
+ * more details.
+ *
+ * Layout is based on skeletonfb.c by James Simmons and Geert Uytterhoeven.
+ *
+ * This driver was written to be used with the Arc LCD board. Arc uses a
+ * set of KS108 chips that control individual 64x64 LCD matrices. The board
+ * can be paneled in a variety of setups such as 2x1=128x64, 4x4=256x256 and
+ * so on. The interface between the board and the host is TTL based GPIO. The
+ * GPIO requirements are 8 writable data lines and 4+n lines for control. On a
+ * GPIO-less system, the board can be tested by connecting the respective sigs
+ * up to a parallel port connector. The driver requires the IO addresses for
+ * data and control GPIO at load time. It is unable to probe for the
+ * existence of the LCD so it must be told at load time whether it should
+ * be enabled or not.
+ *
+ * Todo:
+ * - testing with 4x4
+ * - testing with interrupt hw
+ *
+ * General notes:
+ * - User must set tuhold. It's in microseconds. According to the 108 spec,
+ *   the hold time is supposed to be at least 1 microsecond.
+ * - User must set num_cols=x num_rows=y, eg: x=2 means 128
+ * - User must set arcfb_enable=1 to enable it
+ * - User must set dio_addr=0xIOADDR cio_addr=0xIOADDR
+ *
+ */
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/mm.h>
+#include <linux/tty.h>
+#include <linux/slab.h>
+#include <linux/vmalloc.h>
+#include <linux/delay.h>
+#include <linux/interrupt.h>
+#include <linux/fb.h>
+#include <linux/init.h>
+#include <linux/arcfb.h>
+
+#include <asm/uaccess.h>
+
+#define floor8(a) (a&(~0x07))
+#define floorXres(a,xres) (a&(~(xres - 1)))
+#define iceil8(a) (((int)((a+7)/8))*8)
+#define ceil64(a) (a|0x3F)
+#define ceilXres(a,xres) (a|(xres - 1))
+
+/* ks108 chipset specific defines and code */
+
+#define KS_SET_DPY_START_LINE 	0xC0
+#define KS_SET_PAGE_NUM 	0xB8
+#define KS_SET_X 		0x40
+#define KS_CEHI 		0x01
+#define KS_CELO 		0x00
+#define KS_SEL_CMD 		0x08
+#define KS_SEL_DATA 		0x00
+#define KS_DPY_ON 		0x3F
+#define KS_DPY_OFF 		0x3E
+#define KS_INTACK 		0x40
+#define KS_CLRINT		0x02
+
+struct arcfb_par {
+	unsigned long dio_addr;
+	unsigned long cio_addr;
+	unsigned long c2io_addr;
+	atomic_t ref_count;
+	unsigned char cslut[9];
+	struct fb_info *info;
+	unsigned int irq;
+	spinlock_t lock;
+};
+
+static struct fb_fix_screeninfo arcfb_fix __initdata = {
+	.id =		"arcfb",
+	.type =		FB_TYPE_PACKED_PIXELS,
+	.visual =	FB_VISUAL_MONO01,
+	.xpanstep =	0,
+	.ypanstep =	1,
+	.ywrapstep =	0,
+	.accel =	FB_ACCEL_NONE,
+};
+
+static struct fb_var_screeninfo arcfb_var __initdata = {
+	.xres		= 128,
+	.yres		= 64,
+	.xres_virtual	= 128,
+	.yres_virtual	= 64,
+	.bits_per_pixel	= 1,
+	.nonstd		= 1,
+};
+
+static unsigned long num_cols;
+static unsigned long num_rows;
+static unsigned long dio_addr;
+static unsigned long cio_addr;
+static unsigned long c2io_addr;
+static unsigned long splashval;
+static unsigned long tuhold;
+static unsigned int nosplash;
+static unsigned int arcfb_enable;
+static unsigned int irq;
+
+static DECLARE_WAIT_QUEUE_HEAD(arcfb_waitq);
+
+static void ks108_writeb_ctl(struct arcfb_par *par,
+				unsigned int chipindex, unsigned char value)
+{
+	unsigned char chipselval = par->cslut[chipindex];
+
+	outb(chipselval|KS_CEHI|KS_SEL_CMD, par->cio_addr);
+	outb(value, par->dio_addr);
+	udelay(tuhold);
+	outb(chipselval|KS_CELO|KS_SEL_CMD, par->cio_addr);
+}
+
+static void ks108_writeb_mainctl(struct arcfb_par *par, unsigned char value)
+{
+
+	outb(value, par->cio_addr);
+	udelay(tuhold);
+}
+
+static unsigned char ks108_readb_ctl2(struct arcfb_par *par)
+{
+	return inb(par->c2io_addr);
+}
+
+static void ks108_writeb_data(struct arcfb_par *par,
+				unsigned int chipindex, unsigned char value)
+{
+	unsigned char chipselval = par->cslut[chipindex];
+
+	outb(chipselval|KS_CEHI|KS_SEL_DATA, par->cio_addr);
+	outb(value, par->dio_addr);
+	udelay(tuhold);
+	outb(chipselval|KS_CELO|KS_SEL_DATA, par->cio_addr);
+}
+
+static void ks108_set_start_line(struct arcfb_par *par,
+				unsigned int chipindex, unsigned char y)
+{
+	ks108_writeb_ctl(par, chipindex, KS_SET_DPY_START_LINE|y);
+}
+
+static void ks108_set_yaddr(struct arcfb_par *par,
+				unsigned int chipindex, unsigned char y)
+{
+	ks108_writeb_ctl(par, chipindex, KS_SET_PAGE_NUM|y);
+}
+
+static void ks108_set_xaddr(struct arcfb_par *par,
+				unsigned int chipindex, unsigned char x)
+{
+	ks108_writeb_ctl(par, chipindex, KS_SET_X|x);
+}
+
+static void ks108_clear_lcd(struct arcfb_par *par, unsigned int chipindex)
+{
+	int i,j;
+
+	for (i = 0; i <= 8; i++) {
+		ks108_set_yaddr(par, chipindex, i);
+		ks108_set_xaddr(par, chipindex, 0);
+		for (j = 0; j < 64; j++) {
+			ks108_writeb_data(par, chipindex,
+				(unsigned char) splashval);
+		}
+	}
+}
+
+/* main arcfb functions */
+
+static int arcfb_open(struct fb_info *info, int user)
+{
+	struct arcfb_par *par = info->par;
+
+	atomic_inc(&par->ref_count);
+	return 0;
+}
+
+static int arcfb_release(struct fb_info *info, int user)
+{
+	struct arcfb_par *par = info->par;
+	int count = atomic_read(&par->ref_count);
+
+	if (!count)
+		return -EINVAL;
+	atomic_dec(&par->ref_count);
+	return 0;
+}
+
+static int arcfb_pan_display(struct fb_var_screeninfo *var,
+				struct fb_info *info)
+{
+	int i;
+	struct arcfb_par *par = info->par;
+
+	if ((var->vmode & FB_VMODE_YWRAP) && (var->yoffset < 64)
+		&& (info->var.yres <= 64)) {
+		for (i = 0; i < num_cols; i++) {
+			ks108_set_start_line(par, i, var->yoffset);
+		}
+		info->var.yoffset = var->yoffset;
+		return 0;
+	}
+
+	return -EINVAL;
+}
+
+static irqreturn_t arcfb_interrupt(int vec, void *dev_instance,
+		struct pt_regs *regs)
+{
+	struct fb_info *info = dev_instance;
+	unsigned char ctl2status;
+	struct arcfb_par *par = info->par;
+
+	ctl2status = ks108_readb_ctl2(par);
+
+	if (!(ctl2status & KS_INTACK)) /* not arc generated interrupt */
+		return IRQ_NONE;
+
+	ks108_writeb_mainctl(par, KS_CLRINT);
+
+	spin_lock(&par->lock);
+        if (waitqueue_active(&arcfb_waitq)) {
+                wake_up(&arcfb_waitq);
+        }
+	spin_unlock(&par->lock);
+
+	return IRQ_HANDLED;
+}
+
+/*
+ * here we handle a specific page on the lcd. the complexity comes from
+ * the fact that the fb is laidout in 8xX vertical columns. we extract
+ * each write of 8 vertical pixels. then we shift out as we move along
+ * X. That's what rightshift does. bitmask selects the desired input bit.
+ */
+static void arcfb_lcd_update_page(struct arcfb_par *par, unsigned int upper,
+		unsigned int left, unsigned int right, unsigned int distance)
+{
+	unsigned char *src;
+	unsigned int xindex, yindex, chipindex, linesize;
+	int i, count;
+	unsigned char val;
+	unsigned char bitmask, rightshift;
+
+	xindex = left >> 6;
+	yindex = upper >> 6;
+	chipindex = (xindex + (yindex*num_cols));
+
+	ks108_set_yaddr(par, chipindex, upper/8);
+
+	linesize = par->info->var.xres/8;
+	src = par->info->screen_base + (left/8) + (upper * linesize);
+	ks108_set_xaddr(par, chipindex, left);
+
+	bitmask=1;
+	rightshift=0;
+	while (left <= right) {
+		val = 0;
+		for (i = 0; i < 8; i++) {
+			if ( i > rightshift) {
+				val |= (*(src + (i*linesize)) & bitmask)
+						<< (i - rightshift);
+			} else {
+				val |= (*(src + (i*linesize)) & bitmask)
+						 >> (rightshift - i);
+			}
+		}
+		ks108_writeb_data(par, chipindex, val);
+		left++;
+		count++;
+		if (bitmask == 0x80) {
+			bitmask = 1;
+			src++;
+			rightshift=0;
+		} else {
+			bitmask <<= 1;
+			rightshift++;
+		}
+	}
+}
+
+/*
+ * here we handle the entire vertical page of the update. we write across
+ * lcd chips. update_page uses the upper/left values to decide which
+ * chip to select for the right. upper is needed for setting the page
+ * desired for the write.
+ */
+static void arcfb_lcd_update_vert(struct arcfb_par *par, unsigned int top,
+		unsigned int bottom, unsigned int left, unsigned int right)
+{
+	unsigned int distance, upper, lower;
+
+	distance = (bottom - top) + 1;
+	upper = top;
+	lower = top + 7;
+
+	while (distance > 0) {
+		distance -= 8;
+		arcfb_lcd_update_page(par, upper, left, right, 8);
+		upper = lower + 1;
+		lower = upper + 7;
+	}
+}
+
+/*
+ * here we handle horizontal blocks for the update. update_vert will
+ * handle spaning multiple pages. we break out each horizontal
+ * block in to individual blocks no taller than 64 pixels.
+ */
+static void arcfb_lcd_update_horiz(struct arcfb_par *par, unsigned int left,
+			unsigned int right, unsigned int top, unsigned int h)
+{
+	unsigned int distance, upper, lower;
+
+	distance = h;
+	upper = floor8(top);
+	lower = min(upper + distance - 1, ceil64(upper));
+
+	while (distance > 0) {
+		distance -= ((lower - upper) + 1 );
+		arcfb_lcd_update_vert(par, upper, lower, left, right);
+		upper = lower + 1;
+		lower = min(upper + distance - 1, ceil64(upper));
+	}
+}
+
+/*
+ * here we start the process of spliting out the fb update into
+ * individual blocks of pixels. we end up spliting into 64x64 blocks
+ * and finally down to 64x8 pages.
+ */
+static void arcfb_lcd_update(struct arcfb_par *par, unsigned int dx,
+			unsigned int dy, unsigned int w, unsigned int h)
+{
+	unsigned int left, right, distance, y;
+
+	/* align the request first */
+	y = floor8(dy);
+	h += dy - y;
+	h = iceil8(h);
+
+	distance = w;
+	left = dx;
+	right = min(left + w - 1, ceil64(left));
+
+	while (distance > 0) {
+		arcfb_lcd_update_horiz(par, left, right, y, h);
+		distance -= ((right - left) + 1);
+		left = right + 1;
+		right = min(left + distance - 1, ceil64(left));
+	}
+}
+
+void arcfb_fillrect(struct fb_info *info, const struct fb_fillrect *rect)
+{
+	struct arcfb_par *par = info->par;
+
+	cfb_fillrect(info, rect);
+
+	/* update the physical lcd */
+	arcfb_lcd_update(par, rect->dx, rect->dy, rect->width, rect->height);
+}
+
+void arcfb_copyarea(struct fb_info *info, const struct fb_copyarea *area)
+{
+	struct arcfb_par *par = info->par;
+
+	cfb_copyarea(info, area);
+
+	/* update the physical lcd */
+	arcfb_lcd_update(par, area->dx, area->dy, area->width, area->height);
+}
+
+void arcfb_imageblit(struct fb_info *info, const struct fb_image *image)
+{
+	struct arcfb_par *par = info->par;
+
+	cfb_imageblit(info, image);
+
+	/* update the physical lcd */
+	arcfb_lcd_update(par, image->dx, image->dy, image->width,
+				image->height);
+}
+
+static int arcfb_ioctl(struct inode *inode, struct file *file,
+			  unsigned int cmd, unsigned long arg,
+			  struct fb_info *info)
+{
+	void __user *argp = (void __user *)arg;
+	struct arcfb_par *par = info->par;
+	unsigned long flags;
+
+	switch (cmd) {
+		case FBIO_WAITEVENT:
+		{
+			DEFINE_WAIT(wait);
+			/* illegal to wait on arc if no irq will occur */
+			if (!par->irq)
+				return -EINVAL;
+
+			/* wait until the Arc has generated an interrupt
+			 * which will wake us up */
+			spin_lock_irqsave(&par->lock, flags);
+			prepare_to_wait(&arcfb_waitq, &wait,
+					TASK_INTERRUPTIBLE);
+			spin_unlock_irqrestore(&par->lock, flags);
+			schedule();
+			finish_wait(&arcfb_waitq, &wait);
+		}
+		case FBIO_GETCONTROL2:
+		{
+			unsigned char ctl2;
+
+			ctl2 = ks108_readb_ctl2(info->par);
+			if (copy_to_user(argp, &ctl2, sizeof(ctl2)))
+				return -EFAULT;
+			return 0;
+		}
+		default:
+			return -EINVAL;
+	}
+}
+
+/*
+ * this is the access path from userspace. they can seek and write to
+ * the fb. it's inefficient for them to do anything less than 64*8
+ * writes since we update the lcd in each write() anyway.
+ */
+static ssize_t arcfb_write(struct file *file, const char *buf, size_t count,
+				loff_t *ppos)
+{
+	/* modded from epson 1355 */
+
+	struct inode *inode;
+	int fbidx;
+	struct fb_info *info;
+	unsigned long p;
+	int err=-EINVAL;
+	unsigned int fbmemlength,x,y,w,h, bitppos, startpos, endpos, bitcount;
+	struct arcfb_par *par;
+	unsigned int xres;
+
+	p = *ppos;
+	inode = file->f_dentry->d_inode;
+	fbidx = iminor(inode);
+	info = registered_fb[fbidx];
+	par = info->par;
+
+	if (!info || !info->screen_base)
+		return -ENODEV;
+
+	xres = info->var.xres;
+	fbmemlength = (xres * info->var.yres)/8;
+
+	if (p > fbmemlength)
+		return -ENOSPC;
+
+	err = 0;
+	if ((count + p) > fbmemlength) {
+		count = fbmemlength - p;
+		err = -ENOSPC;
+	}
+
+	if (count) {
+		char *base_addr;
+
+		base_addr = info->screen_base;
+		count -= copy_from_user(base_addr + p, buf, count);
+		*ppos += count;
+		err = -EFAULT;
+	}
+
+
+	bitppos = p*8;
+	startpos = floorXres(bitppos, xres);
+	endpos = ceilXres((bitppos + (count*8)), xres);
+	bitcount = endpos - startpos;
+
+	x = startpos % xres;
+	y = startpos / xres;
+	w = xres;
+	h = bitcount / xres;
+	arcfb_lcd_update(par, x, y, w, h);
+
+	if (count)
+		return count;
+	return err;
+}
+
+static void arcfb_platform_release(struct device *device)
+{
+}
+
+static struct fb_ops arcfb_ops = {
+	.owner		= THIS_MODULE,
+	.fb_open	= arcfb_open,
+	.fb_write	= arcfb_write,
+	.fb_release	= arcfb_release,
+	.fb_pan_display	= arcfb_pan_display,
+	.fb_fillrect	= arcfb_fillrect,
+	.fb_copyarea	= arcfb_copyarea,
+	.fb_imageblit	= arcfb_imageblit,
+	.fb_cursor	= soft_cursor,
+	.fb_ioctl 	= arcfb_ioctl,
+};
+
+static int __init arcfb_probe(struct device *device)
+{
+	struct platform_device *dev = to_platform_device(device);
+	struct fb_info *info;
+	int retval = -ENOMEM;
+	int videomemorysize;
+	unsigned char *videomemory;
+	struct arcfb_par *par;
+	int i;
+
+	videomemorysize = (((64*64)*num_cols)*num_rows)/8;
+
+	/* We need a flat backing store for the Arc's
+	   less-flat actual paged framebuffer */
+	if (!(videomemory = vmalloc(videomemorysize)))
+		return retval;
+
+	memset(videomemory, 0, videomemorysize);
+
+	info = framebuffer_alloc(sizeof(struct arcfb_par), &dev->dev);
+	if (!info)
+		goto err;
+
+	info->screen_base = (char __iomem *)videomemory;
+	info->fbops = &arcfb_ops;
+
+	info->var = arcfb_var;
+	info->fix = arcfb_fix;
+	par = info->par;
+	par->info = info;
+
+	if (!dio_addr || !cio_addr || !c2io_addr) {
+		printk(KERN_WARNING "no IO addresses supplied\n");
+		goto err1;
+	}
+	par->dio_addr = dio_addr;
+	par->cio_addr = cio_addr;
+	par->c2io_addr = c2io_addr;
+	par->cslut[0] = 0x00;
+	par->cslut[1] = 0x06;
+	info->flags = FBINFO_FLAG_DEFAULT;
+	spin_lock_init(&par->lock);
+	retval = register_framebuffer(info);
+	if (retval < 0)
+		goto err1;
+	dev_set_drvdata(&dev->dev, info);
+	if (irq) {
+		par->irq = irq;
+		if (request_irq(par->irq, &arcfb_interrupt, SA_SHIRQ,
+				"arcfb", info)) {
+			printk(KERN_INFO
+				"arcfb: Failed req IRQ %d\n", par->irq);
+			goto err1;
+		}
+	}
+	printk(KERN_INFO
+	       "fb%d: Arc frame buffer device, using %dK of video memory\n",
+	       info->node, videomemorysize >> 10);
+
+	/* this inits the lcd but doesn't clear dirty pixels */
+	for (i = 0; i < num_cols * num_rows; i++) {
+		ks108_writeb_ctl(par, i, KS_DPY_OFF);
+		ks108_set_start_line(par, i, 0);
+		ks108_set_yaddr(par, i, 0);
+		ks108_set_xaddr(par, i, 0);
+		ks108_writeb_ctl(par, i, KS_DPY_ON);
+	}
+
+	/* if we were told to splash the screen, we just clear it */
+	if (!nosplash) {
+		for (i = 0; i < num_cols * num_rows; i++) {
+			printk(KERN_INFO "fb%d: splashing lcd %d\n",
+				info->node, i);
+			ks108_set_start_line(par, i, 0);
+			ks108_clear_lcd(par, i);
+		}
+	}
+
+	return 0;
+err1:
+	framebuffer_release(info);
+err:
+	vfree(videomemory);
+	return retval;
+}
+
+static int arcfb_remove(struct device *device)
+{
+	struct fb_info *info = dev_get_drvdata(device);
+
+	if (info) {
+		unregister_framebuffer(info);
+		vfree(info->screen_base);
+		framebuffer_release(info);
+	}
+	return 0;
+}
+
+static struct device_driver arcfb_driver = {
+	.name	= "arcfb",
+	.bus	= &platform_bus_type,
+	.probe	= arcfb_probe,
+	.remove = arcfb_remove,
+};
+
+static struct platform_device arcfb_device = {
+	.name	= "arcfb",
+	.id	= 0,
+	.dev	= {
+		.release = arcfb_platform_release,
+	}
+};
+
+static int __init arcfb_init(void)
+{
+	int ret;
+
+	if (!arcfb_enable)
+		return -ENXIO;
+
+	ret = driver_register(&arcfb_driver);
+	if (!ret) {
+		ret = platform_device_register(&arcfb_device);
+		if (ret)
+			driver_unregister(&arcfb_driver);
+	}
+	return ret;
+
+}
+
+static void __exit arcfb_exit(void)
+{
+	platform_device_unregister(&arcfb_device);
+	driver_unregister(&arcfb_driver);
+}
+
+module_param(num_cols, ulong, 0);
+MODULE_PARM_DESC(num_cols, "Num horiz panels, eg: 2 = 128 bit wide");
+module_param(num_rows, ulong, 0);
+MODULE_PARM_DESC(num_rows, "Num vert panels, eg: 1 = 64 bit high");
+module_param(nosplash, uint, 0);
+MODULE_PARM_DESC(nosplash, "Disable doing the splash screen");
+module_param(arcfb_enable, uint, 0);
+MODULE_PARM_DESC(arcfb_enable, "Enable communication with Arc board");
+module_param(dio_addr, ulong, 0);
+MODULE_PARM_DESC(dio_addr, "IO address for data, eg: 0x480");
+module_param(cio_addr, ulong, 0);
+MODULE_PARM_DESC(cio_addr, "IO address for control, eg: 0x400");
+module_param(c2io_addr, ulong, 0);
+MODULE_PARM_DESC(c2io_addr, "IO address for secondary control, eg: 0x408");
+module_param(splashval, ulong, 0);
+MODULE_PARM_DESC(splashval, "Splash pattern: 0xFF is black, 0x00 is green");
+module_param(tuhold, ulong, 0);
+MODULE_PARM_DESC(tuhold, "Time to hold between strobing data to Arc board");
+module_param(irq, uint, 0);
+MODULE_PARM_DESC(irq, "IRQ for the Arc board");
+
+module_init(arcfb_init);
+module_exit(arcfb_exit);
+
+MODULE_DESCRIPTION("fbdev driver for Arc monochrome LCD board");
+MODULE_AUTHOR("Jaya Kumar");
+MODULE_LICENSE("GPL");
+
diff --git a/drivers/video/chipsfb.c b/drivers/video/chipsfb.c
index ab98f22..95e7255 100644
--- a/drivers/video/chipsfb.c
+++ b/drivers/video/chipsfb.c
@@ -423,9 +423,6 @@
 	pmu_register_sleep_notifier(&chips_sleep_notifier);
 #endif /* CONFIG_PMAC_PBOOK */
 
-	/* Clear the entire framebuffer */
-	memset(p->screen_base, 0, 0x100000);
-
 	pci_set_drvdata(dp, p);
 	return 0;
 }
diff --git a/drivers/video/console/Kconfig b/drivers/video/console/Kconfig
index ccf5581..e4b91a4 100644
--- a/drivers/video/console/Kconfig
+++ b/drivers/video/console/Kconfig
@@ -153,6 +153,15 @@
 	  Small console font with Macintosh-style high-half glyphs.  Some Mac
 	  framebuffer drivers don't support this one at all.
 
+config FONT_7x14
+	bool "console 7x14 font (not supported by all drivers)" if FONTS
+	depends on FRAMEBUFFER_CONSOLE
+	default y if !SPARC32 && !SPARC64 && !FONTS
+	help
+	  Console font with characters just a bit smaller than the default.
+	  If the standard 8x16 font is a little too big for you, say Y.
+	  Otherwise, say N.
+
 config FONT_PEARL_8x8
 	bool "Pearl (old m68k) console 8x8 font" if FONTS
 	depends on FRAMEBUFFER_CONSOLE
@@ -187,5 +196,13 @@
 	  big letters (like the letters used in the SPARC PROM). If the
 	  standard font is unreadable for you, say Y, otherwise say N.
 
+config FONT_10x18
+	bool "console 10x18 font (not supported by all drivers)"
+	depends on FONTS
+	help
+	  This is a high resolution console font for machines with very
+	  big letters. It fits between the sun 12x22 and the normal 8x16 font.
+	  If other fonts are too big or too small for you, say Y, otherwise say N.
+
 endmenu
 
diff --git a/drivers/video/console/Makefile b/drivers/video/console/Makefile
index 3351644..b562f6b 100644
--- a/drivers/video/console/Makefile
+++ b/drivers/video/console/Makefile
@@ -10,6 +10,8 @@
 font-objs-$(CONFIG_FONT_8x8)       += font_8x8.o
 font-objs-$(CONFIG_FONT_8x16)      += font_8x16.o
 font-objs-$(CONFIG_FONT_6x11)      += font_6x11.o
+font-objs-$(CONFIG_FONT_7x14)      += font_7x14.o
+font-objs-$(CONFIG_FONT_10x18)     += font_10x18.o
 font-objs-$(CONFIG_FONT_PEARL_8x8) += font_pearl_8x8.o
 font-objs-$(CONFIG_FONT_ACORN_8x8) += font_acorn_8x8.o
 font-objs-$(CONFIG_FONT_MINI_4x6)  += font_mini_4x6.o
diff --git a/drivers/video/console/bitblit.c b/drivers/video/console/bitblit.c
index b28a4b0..3c73157 100644
--- a/drivers/video/console/bitblit.c
+++ b/drivers/video/console/bitblit.c
@@ -107,13 +107,6 @@
 		      const unsigned short *s, int count, int yy, int xx,
 		      int fg, int bg)
 {
-	void (*move_unaligned)(struct fb_info *info, struct fb_pixmap *buf,
-			       u8 *dst, u32 d_pitch, u8 *src, u32 idx,
-			       u32 height, u32 shift_high, u32 shift_low,
-			       u32 mod);
-	void (*move_aligned)(struct fb_info *info, struct fb_pixmap *buf,
-			     u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch,
-			     u32 height);
 	unsigned short charmask = vc->vc_hi_font_mask ? 0x1ff : 0xff;
 	unsigned int width = (vc->vc_font.width + 7) >> 3;
 	unsigned int cellsize = vc->vc_font.height * width;
@@ -141,13 +134,6 @@
 	image.height = vc->vc_font.height;
 	image.depth = 1;
 
-	if (info->pixmap.outbuf && info->pixmap.inbuf) {
-		move_aligned = fb_iomove_buf_aligned;
-		move_unaligned = fb_iomove_buf_unaligned;
-	} else {
-		move_aligned = fb_sysmove_buf_aligned;
-		move_unaligned = fb_sysmove_buf_unaligned;
-	}
 	while (count) {
 		if (count > maxcnt)
 			cnt = k = maxcnt;
@@ -171,9 +157,9 @@
 					src = buf;
 				}
 
-				move_unaligned(info, &info->pixmap, dst, pitch,
-					       src, idx, image.height,
-					       shift_high, shift_low, mod);
+				fb_pad_unaligned_buffer(dst, pitch, src, idx,
+						image.height, shift_high,
+						shift_low, mod);
 				shift_low += mod;
 				dst += (shift_low >= 8) ? width : width - 1;
 				shift_low &= 7;
@@ -189,8 +175,7 @@
 					src = buf;
 				}
 
-				move_aligned(info, &info->pixmap, dst, pitch,
-					     src, idx, image.height);
+				fb_pad_aligned_buffer(dst, pitch, src, idx, image.height);
 				dst += width;
 			}
 		}
diff --git a/drivers/video/console/font_10x18.c b/drivers/video/console/font_10x18.c
new file mode 100644
index 0000000..ff0af96
--- /dev/null
+++ b/drivers/video/console/font_10x18.c
@@ -0,0 +1,5146 @@
+/********************************
+ * adapted from font_sun12x22.c *
+ * by Jurriaan Kalkman 06-2005  *
+ ********************************/
+
+#include <linux/font.h>
+
+#define FONTDATAMAX 9216
+
+static unsigned char fontdata_10x18[FONTDATAMAX] = {
+
+	/* 0 0x00 '^@' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 1 0x01 '^A' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x80, /* 0011111110 */
+	0x40, 0x40, /* 0100000001 */
+	0x5b, 0x40, /* 0101101101 */
+	0x40, 0x40, /* 0100000001 */
+	0x44, 0x40, /* 0100010001 */
+	0x44, 0x40, /* 0100010001 */
+	0x51, 0x40, /* 0101000101 */
+	0x4e, 0x40, /* 0100111001 */
+	0x40, 0x40, /* 0100000001 */
+	0x3f, 0x80, /* 0011111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 2 0x02 '^B' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x80, /* 0011111110 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x64, 0xc0, /* 0110010011 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x7b, 0xc0, /* 0111101111 */
+	0x7b, 0xc0, /* 0111101111 */
+	0x6e, 0xc0, /* 0110111011 */
+	0x71, 0xc0, /* 0111000111 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x3f, 0x80, /* 0011111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 3 0x03 '^C' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x11, 0x00, /* 0001000100 */
+	0x3b, 0x80, /* 0011101110 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x3f, 0x80, /* 0011111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x04, 0x00, /* 0000010000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 4 0x04 '^D' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x3f, 0x80, /* 0011111110 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x04, 0x00, /* 0000010000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 5 0x05 '^E' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x31, 0x80, /* 0011000110 */
+	0x7b, 0xc0, /* 0111101111 */
+	0x35, 0x80, /* 0011010110 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 6 0x06 '^F' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x3f, 0x80, /* 0011111110 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x35, 0x80, /* 0011010110 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 7 0x07 '^G' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 8 0x08 '^H' */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xf3, 0xc0, /* 1111001111 */
+	0xe1, 0xc0, /* 1110000111 */
+	0xe1, 0xc0, /* 1110000111 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xe1, 0xc0, /* 1110000111 */
+	0xe1, 0xc0, /* 1110000111 */
+	0xf3, 0xc0, /* 1111001111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+
+	/* 9 0x09 '^I' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x12, 0x00, /* 0001001000 */
+	0x12, 0x00, /* 0001001000 */
+	0x21, 0x00, /* 0010000100 */
+	0x21, 0x00, /* 0010000100 */
+	0x12, 0x00, /* 0001001000 */
+	0x12, 0x00, /* 0001001000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 10 0x0a '^J' */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xf3, 0xc0, /* 1111001111 */
+	0xed, 0xc0, /* 1110110111 */
+	0xed, 0xc0, /* 1110110111 */
+	0xde, 0xc0, /* 1101111011 */
+	0xde, 0xc0, /* 1101111011 */
+	0xed, 0xc0, /* 1110110111 */
+	0xed, 0xc0, /* 1110110111 */
+	0xf3, 0xc0, /* 1111001111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+
+	/* 11 0x0b '^K' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x03, 0xc0, /* 0000001111 */
+	0x06, 0xc0, /* 0000011011 */
+	0x0c, 0xc0, /* 0000110011 */
+	0x3c, 0x00, /* 0011110000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc3, 0x00, /* 1100001100 */
+	0x66, 0x00, /* 0110011000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 12 0x0c '^L' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 13 0x0d '^M' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0x80, /* 0000111110 */
+	0x08, 0x80, /* 0000100010 */
+	0x0f, 0x80, /* 0000111110 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x38, 0x00, /* 0011100000 */
+	0x78, 0x00, /* 0111100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 14 0x0e '^N' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x80, /* 0001111110 */
+	0x10, 0x80, /* 0001000010 */
+	0x1f, 0x80, /* 0001111110 */
+	0x10, 0x80, /* 0001000010 */
+	0x10, 0x80, /* 0001000010 */
+	0x10, 0x80, /* 0001000010 */
+	0x10, 0x80, /* 0001000010 */
+	0x13, 0x80, /* 0001001110 */
+	0x17, 0x80, /* 0001011110 */
+	0x73, 0x00, /* 0111001100 */
+	0xf0, 0x00, /* 1111000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 15 0x0f '^O' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x24, 0x80, /* 0010010010 */
+	0x15, 0x00, /* 0001010100 */
+	0x55, 0x40, /* 0101010101 */
+	0x3f, 0x80, /* 0011111110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x3f, 0x80, /* 0011111110 */
+	0x55, 0x40, /* 0101010101 */
+	0x15, 0x00, /* 0001010100 */
+	0x24, 0x80, /* 0010010010 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 16 0x10 '^P' */
+	0x00, 0x80, /* 0000000010 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x80, /* 0000001110 */
+	0x07, 0x80, /* 0000011110 */
+	0x0f, 0x80, /* 0000111110 */
+	0x1f, 0x80, /* 0001111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0xff, 0x80, /* 1111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x1f, 0x80, /* 0001111110 */
+	0x0f, 0x80, /* 0000111110 */
+	0x07, 0x80, /* 0000011110 */
+	0x03, 0x80, /* 0000001110 */
+	0x01, 0x80, /* 0000000110 */
+	0x00, 0x80, /* 0000000010 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 17 0x11 '^Q' */
+	0x40, 0x00, /* 0100000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x70, 0x00, /* 0111000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x7c, 0x00, /* 0111110000 */
+	0x7e, 0x00, /* 0111111000 */
+	0x7f, 0x00, /* 0111111100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x00, /* 0111111100 */
+	0x7e, 0x00, /* 0111111000 */
+	0x7c, 0x00, /* 0111110000 */
+	0x78, 0x00, /* 0111100000 */
+	0x70, 0x00, /* 0111000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x40, 0x00, /* 0100000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 18 0x12 '^R' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 19 0x13 '^S' */
+	0x00, 0x00, /* 0000000000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 20 0x14 '^T' */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x39, 0x80, /* 0011100110 */
+	0x79, 0x80, /* 0111100110 */
+	0x79, 0x80, /* 0111100110 */
+	0x79, 0x80, /* 0111100110 */
+	0x39, 0x80, /* 0011100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x39, 0xc0, /* 0011100111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 21 0x15 '^U' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 22 0x16 '^V' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 23 0x17 '^W' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 24 0x18 '^X' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 25 0x19 '^Y' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 26 0x1a '^Z' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x06, 0x00, /* 0000011000 */
+	0x07, 0x00, /* 0000011100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x07, 0x00, /* 0000011100 */
+	0x06, 0x00, /* 0000011000 */
+	0x04, 0x00, /* 0000010000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 27 0x1b '^[' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x08, 0x00, /* 0000100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x38, 0x00, /* 0011100000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x38, 0x00, /* 0011100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 28 0x1c '^\' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 29 0x1d '^]' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x12, 0x00, /* 0001001000 */
+	0x33, 0x00, /* 0011001100 */
+	0x73, 0x80, /* 0111001110 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x73, 0x80, /* 0111001110 */
+	0x33, 0x00, /* 0011001100 */
+	0x12, 0x00, /* 0001001000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 30 0x1e '^^' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x3f, 0x80, /* 0011111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 31 0x1f '^_' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x3f, 0x80, /* 0011111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x04, 0x00, /* 0000010000 */
+	0x04, 0x00, /* 0000010000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 32 0x20 ' ' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 33 0x21 '!' */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 34 0x22 '"' */
+	0x00, 0x00, /* 0000000000 */
+	0x63, 0x00, /* 0110001100 */
+	0xf7, 0x80, /* 1111011110 */
+	0xf7, 0x80, /* 1111011110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x42, 0x00, /* 0100001000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 35 0x23 '#' */
+	0x00, 0x00, /* 0000000000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 36 0x24 '$' */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x6f, 0x80, /* 0110111110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6c, 0x80, /* 0110110010 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0f, 0x00, /* 0000111100 */
+	0x0d, 0x80, /* 0000110110 */
+	0x4d, 0x80, /* 0100110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x7f, 0x00, /* 0111111100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 37 0x25 '%' */
+	0x00, 0x00, /* 0000000000 */
+	0x31, 0x80, /* 0011000110 */
+	0x7b, 0x00, /* 0111101100 */
+	0x7b, 0x00, /* 0111101100 */
+	0x36, 0x00, /* 0011011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x37, 0x80, /* 0011011110 */
+	0x37, 0x80, /* 0011011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 38 0x26 '&' */
+	0x00, 0x00, /* 0000000000 */
+	0x07, 0x00, /* 0000011100 */
+	0x0f, 0x80, /* 0000111110 */
+	0x19, 0x80, /* 0001100110 */
+	0x19, 0x80, /* 0001100110 */
+	0x0f, 0x80, /* 0000111110 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x76, 0x00, /* 0111011000 */
+	0x66, 0x40, /* 0110011001 */
+	0x63, 0xc0, /* 0110001111 */
+	0x63, 0x80, /* 0110001110 */
+	0x63, 0x00, /* 0110001100 */
+	0x3f, 0x80, /* 0011111110 */
+	0x1c, 0xc0, /* 0001110011 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 39 0x27 ''' */
+	0x00, 0x00, /* 0000000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x78, 0x00, /* 0111100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x20, 0x00, /* 0010000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 40 0x28 '(' */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x03, 0x00, /* 0000001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 41 0x29 ')' */
+	0x00, 0x00, /* 0000000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 42 0x2a '*' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x4c, 0x80, /* 0100110010 */
+	0x6d, 0x80, /* 0110110110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x7f, 0x80, /* 0111111110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x6d, 0x80, /* 0110110110 */
+	0x4c, 0x80, /* 0100110010 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 43 0x2b '+' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 44 0x2c ',' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x78, 0x00, /* 0111100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x40, 0x00, /* 0100000000 */
+
+	/* 45 0x2d '-' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 46 0x2e '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 47 0x2f '/' */
+	0x00, 0x00, /* 0000000000 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 48 0x30 '0' */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x23, 0x00, /* 0010001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x63, 0x80, /* 0110001110 */
+	0x65, 0x80, /* 0110010110 */
+	0x65, 0x80, /* 0110010110 */
+	0x69, 0x80, /* 0110100110 */
+	0x69, 0x80, /* 0110100110 */
+	0x71, 0x80, /* 0111000110 */
+	0x61, 0x00, /* 0110000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 49 0x31 '1' */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 50 0x32 '2' */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x63, 0x80, /* 0110001110 */
+	0x41, 0x80, /* 0100000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x80, /* 0011000010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 51 0x33 '3' */
+	0x00, 0x00, /* 0000000000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x47, 0x00, /* 0100011100 */
+	0x03, 0x00, /* 0000001100 */
+	0x07, 0x00, /* 0000011100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x07, 0x00, /* 0000011100 */
+	0x03, 0x00, /* 0000001100 */
+	0x01, 0x80, /* 0000000110 */
+	0x41, 0x80, /* 0100000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 52 0x34 '4' */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x66, 0x00, /* 0110011000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc6, 0x00, /* 1100011000 */
+	0xc6, 0x00, /* 1100011000 */
+	0xff, 0x80, /* 1111111110 */
+	0xff, 0x80, /* 1111111110 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 53 0x35 '5' */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x7e, 0x00, /* 0111111000 */
+	0x67, 0x00, /* 0110011100 */
+	0x03, 0x80, /* 0000001110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x41, 0x80, /* 0100000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 54 0x36 '6' */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x6e, 0x00, /* 0110111000 */
+	0x7f, 0x00, /* 0111111100 */
+	0x73, 0x80, /* 0111001110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x71, 0x00, /* 0111000100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 55 0x37 '7' */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x80, /* 0001111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x61, 0x80, /* 0110000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 56 0x38 '8' */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x23, 0x00, /* 0010001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x31, 0x00, /* 0011000100 */
+	0x1a, 0x00, /* 0001101000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x16, 0x00, /* 0001011000 */
+	0x23, 0x00, /* 0010001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x31, 0x00, /* 0011000100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 57 0x39 '9' */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x17, 0x00, /* 0001011100 */
+	0x23, 0x80, /* 0010001110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0x80, /* 0011110110 */
+	0x19, 0x80, /* 0001100110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 58 0x3a ':' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 59 0x3b ';' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x20, 0x00, /* 0010000000 */
+
+	/* 60 0x3c '<' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x03, 0x00, /* 0000001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 61 0x3d '=' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 62 0x3e '>' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x03, 0x00, /* 0000001100 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 63 0x3f '?' */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x3b, 0x80, /* 0011101110 */
+	0x21, 0x80, /* 0010000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 64 0x40 '@' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x65, 0x80, /* 0110010110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6f, 0x80, /* 0110111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x31, 0x80, /* 0011000110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x0f, 0x00, /* 0000111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 65 0x41 'A' */
+	0x00, 0x00, /* 0000000000 */
+	0x04, 0x00, /* 0000010000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x19, 0x80, /* 0001100110 */
+	0x31, 0x80, /* 0011000110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x31, 0x80, /* 0011000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x60, 0xc0, /* 0110000011 */
+	0x60, 0xc0, /* 0110000011 */
+	0xf1, 0xc0, /* 1111000111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 66 0x42 'B' */
+	0x00, 0x00, /* 0000000000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x62, 0x00, /* 0110001000 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x66, 0x00, /* 0110011000 */
+	0x7e, 0x00, /* 0111111000 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x63, 0x00, /* 0110001100 */
+	0xfe, 0x00, /* 1111111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 67 0x43 'C' */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0x00, /* 0000111100 */
+	0x11, 0x80, /* 0001000110 */
+	0x20, 0x80, /* 0010000010 */
+	0x20, 0x00, /* 0010000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x20, 0x00, /* 0010000000 */
+	0x30, 0x80, /* 0011000010 */
+	0x19, 0x00, /* 0001100100 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 68 0x44 'D' */
+	0x00, 0x00, /* 0000000000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x67, 0x00, /* 0110011100 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x00, /* 0110000100 */
+	0x66, 0x00, /* 0110011000 */
+	0xf8, 0x00, /* 1111100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 69 0x45 'E' */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x31, 0x00, /* 0011000100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x31, 0x00, /* 0011000100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 70 0x46 'F' */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x31, 0x00, /* 0011000100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x31, 0x00, /* 0011000100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 71 0x47 'G' */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0x00, /* 0000111100 */
+	0x11, 0x80, /* 0001000110 */
+	0x20, 0x80, /* 0010000010 */
+	0x20, 0x00, /* 0010000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x67, 0xc0, /* 0110011111 */
+	0x61, 0x80, /* 0110000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x19, 0x80, /* 0001100110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 72 0x48 'H' */
+	0x00, 0x00, /* 0000000000 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 73 0x49 'I' */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 74 0x4a 'J' */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x08, 0x00, /* 0000100000 */
+	0x70, 0x00, /* 0111000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 75 0x4b 'K' */
+	0x00, 0x00, /* 0000000000 */
+	0xf1, 0x80, /* 1111000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x66, 0x00, /* 0110011000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x78, 0x00, /* 0111100000 */
+	0x70, 0x00, /* 0111000000 */
+	0x70, 0x00, /* 0111000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x78, 0x00, /* 0111100000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x66, 0x00, /* 0110011000 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0xf0, 0xc0, /* 1111000011 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 76 0x4c 'L' */
+	0x00, 0x00, /* 0000000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 77 0x4d 'M' */
+	0x00, 0x00, /* 0000000000 */
+	0xe0, 0xc0, /* 1110000011 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x73, 0x80, /* 0111001110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 78 0x4e 'N' */
+	0x00, 0x00, /* 0000000000 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x71, 0x80, /* 0111000110 */
+	0x79, 0x80, /* 0111100110 */
+	0x79, 0x80, /* 0111100110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x67, 0x80, /* 0110011110 */
+	0x67, 0x80, /* 0110011110 */
+	0x63, 0x80, /* 0110001110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 79 0x4f 'O' */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x17, 0x00, /* 0001011100 */
+	0x23, 0x00, /* 0010001100 */
+	0x21, 0x80, /* 0010000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x21, 0x00, /* 0010000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x1a, 0x00, /* 0001101000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 80 0x50 'P' */
+	0x00, 0x00, /* 0000000000 */
+	0xfe, 0x00, /* 1111111000 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x7e, 0x00, /* 0111111000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0xf0, 0x00, /* 1111000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 81 0x51 'Q' */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x13, 0x00, /* 0001001100 */
+	0x23, 0x00, /* 0010001100 */
+	0x21, 0x80, /* 0010000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x3b, 0x00, /* 0011101100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x26, 0x00, /* 0010011000 */
+	0x03, 0x80, /* 0000001110 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 82 0x52 'R' */
+	0x00, 0x00, /* 0000000000 */
+	0xfe, 0x00, /* 1111111000 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x00, /* 0110000100 */
+	0x7e, 0x00, /* 0111111000 */
+	0x78, 0x00, /* 0111100000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x6e, 0x00, /* 0110111000 */
+	0x67, 0x00, /* 0110011100 */
+	0x63, 0x80, /* 0110001110 */
+	0x61, 0xc0, /* 0110000111 */
+	0xf0, 0xc0, /* 1111000011 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 83 0x53 'S' */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x03, 0x00, /* 0000001100 */
+	0x01, 0x80, /* 0000000110 */
+	0x41, 0x80, /* 0100000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 84 0x54 'T' */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x4c, 0x80, /* 0100110010 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 85 0x55 'U' */
+	0x00, 0x00, /* 0000000000 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x00, /* 0111001100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 86 0x56 'V' */
+	0x00, 0x00, /* 0000000000 */
+	0xe1, 0xc0, /* 1110000111 */
+	0xc0, 0xc0, /* 1100000011 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x12, 0x00, /* 0001001000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 87 0x57 'W' */
+	0x00, 0x00, /* 0000000000 */
+	0xe1, 0xc0, /* 1110000111 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xe0, 0xc0, /* 1110000011 */
+	0x61, 0x80, /* 0110000110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x77, 0x00, /* 0111011100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 88 0x58 'X' */
+	0x00, 0x00, /* 0000000000 */
+	0xf7, 0x80, /* 1111011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0xf7, 0x80, /* 1111011110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 89 0x59 'Y' */
+	0x00, 0x00, /* 0000000000 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 90 0x5a 'Z' */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x80, /* 0011111110 */
+	0x21, 0x80, /* 0010000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x80, /* 0011000010 */
+	0x3f, 0x80, /* 0011111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 91 0x5b '[' */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x1f, 0x00, /* 0001111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 92 0x5c '\' */
+	0x00, 0x00, /* 0000000000 */
+	0xc0, 0x00, /* 1100000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x00, 0xc0, /* 0000000011 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 93 0x5d ']' */
+	0x00, 0x00, /* 0000000000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 94 0x5e '^' */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 95 0x5f '_' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 96 0x60 '`' */
+	0x04, 0x00, /* 0000010000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 97 0x61 'a' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x07, 0x80, /* 0000011110 */
+	0x39, 0x80, /* 0011100110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0xc0, /* 0011110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 98 0x62 'b' */
+	0x20, 0x00, /* 0010000000 */
+	0x60, 0x00, /* 0110000000 */
+	0xe0, 0x00, /* 1110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x66, 0x00, /* 0110011000 */
+	0x6f, 0x00, /* 0110111100 */
+	0x73, 0x80, /* 0111001110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x71, 0x80, /* 0111000110 */
+	0x7b, 0x00, /* 0111101100 */
+	0x4e, 0x00, /* 0100111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 99 0x63 'c' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x37, 0x00, /* 0011011100 */
+	0x23, 0x00, /* 0010001100 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x71, 0x00, /* 0111000100 */
+	0x33, 0x00, /* 0011001100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 100 0x64 'd' */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x80, /* 0000001110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x0d, 0x80, /* 0000110110 */
+	0x37, 0x80, /* 0011011110 */
+	0x23, 0x80, /* 0010001110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x35, 0x80, /* 0011010110 */
+	0x19, 0xc0, /* 0001100111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 101 0x65 'e' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x19, 0x80, /* 0001100110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 102 0x66 'f' */
+	0x07, 0x00, /* 0000011100 */
+	0x09, 0x80, /* 0000100110 */
+	0x09, 0x80, /* 0000100110 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x7f, 0x00, /* 0111111100 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 103 0x67 'g' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1c, 0x80, /* 0001110010 */
+	0x37, 0x80, /* 0011011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x36, 0x00, /* 0011011000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x60, 0x00, /* 0110000000 */
+	0x7f, 0x00, /* 0111111100 */
+	0x3f, 0x80, /* 0011111110 */
+	0x21, 0x80, /* 0010000110 */
+	0x40, 0x80, /* 0100000010 */
+	0x7f, 0x00, /* 0111111100 */
+	0x3e, 0x00, /* 0011111000 */
+
+	/* 104 0x68 'h' */
+	0x10, 0x00, /* 0001000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x70, 0x00, /* 0111000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x37, 0x00, /* 0011011100 */
+	0x3b, 0x80, /* 0011101110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x7b, 0xc0, /* 0111101111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 105 0x69 'i' */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 106 0x6a 'j' */
+	0x00, 0x00, /* 0000000000 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x07, 0x80, /* 0000011110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x41, 0x80, /* 0100000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x71, 0x80, /* 0111000110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1c, 0x00, /* 0001110000 */
+
+	/* 107 0x6b 'k' */
+	0x60, 0x00, /* 0110000000 */
+	0xe0, 0x00, /* 1110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x63, 0x80, /* 0110001110 */
+	0x66, 0x00, /* 0110011000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x78, 0x00, /* 0111100000 */
+	0x70, 0x00, /* 0111000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x6e, 0x00, /* 0110111000 */
+	0x67, 0x00, /* 0110011100 */
+	0xf3, 0x80, /* 1111001110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 108 0x6c 'l' */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 109 0x6d 'm' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xdb, 0x80, /* 1101101110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0xed, 0xc0, /* 1110110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 110 0x6e 'n' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x6f, 0x00, /* 0110111100 */
+	0x7b, 0x80, /* 0111101110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x7b, 0xc0, /* 0111101111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 111 0x6f 'o' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xe1, 0x80, /* 1110000110 */
+	0x73, 0x00, /* 0111001100 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 112 0x70 'p' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xde, 0x00, /* 1101111000 */
+	0x76, 0x00, /* 0111011000 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x71, 0x80, /* 0111000110 */
+	0x7b, 0x00, /* 0111101100 */
+	0x7e, 0x00, /* 0111111000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0xf0, 0x00, /* 1111000000 */
+
+	/* 113 0x71 'q' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0xc0, /* 0000111011 */
+	0x1b, 0x80, /* 0001101110 */
+	0x33, 0x80, /* 0011001110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x71, 0x80, /* 0111000110 */
+	0x3b, 0x80, /* 0011101110 */
+	0x1f, 0x80, /* 0001111110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0xc0, /* 0000001111 */
+
+	/* 114 0x72 'r' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x73, 0x00, /* 0111001100 */
+	0x35, 0x80, /* 0011010110 */
+	0x39, 0x80, /* 0011100110 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x78, 0x00, /* 0111100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 115 0x73 's' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x00, /* 0110000100 */
+	0x70, 0x00, /* 0111000000 */
+	0x38, 0x00, /* 0011100000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x07, 0x00, /* 0000011100 */
+	0x43, 0x00, /* 0100001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x7e, 0x00, /* 0111111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 116 0x74 't' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x1c, 0x80, /* 0001110010 */
+	0x0f, 0x00, /* 0000111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 117 0x75 'u' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf7, 0x80, /* 1111011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x77, 0x00, /* 0111011100 */
+	0x3d, 0x80, /* 0011110110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 118 0x76 'v' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf1, 0xc0, /* 1111000111 */
+	0x60, 0xc0, /* 0110000011 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x19, 0x80, /* 0001100110 */
+	0x1b, 0x00, /* 0001101100 */
+	0x0f, 0x00, /* 0000111100 */
+	0x0f, 0x00, /* 0000111100 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 119 0x77 'w' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xe3, 0xc0, /* 1110001111 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0x6b, 0x00, /* 0110101100 */
+	0x6b, 0x00, /* 0110101100 */
+	0x7e, 0x00, /* 0111111000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 120 0x78 'x' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf7, 0x80, /* 1111011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x66, 0x00, /* 0110011000 */
+	0x63, 0x00, /* 0110001100 */
+	0xf7, 0x80, /* 1111011110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 121 0x79 'y' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x78, 0x00, /* 0111100000 */
+	0x70, 0x00, /* 0111000000 */
+
+	/* 122 0x7a 'z' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x61, 0x80, /* 0110000110 */
+	0x43, 0x00, /* 0100001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x80, /* 0110000010 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 123 0x7b '{' */
+	0x07, 0x00, /* 0000011100 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x70, 0x00, /* 0111000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x07, 0x00, /* 0000011100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 124 0x7c '|' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 125 0x7d '}' */
+	0x38, 0x00, /* 0011100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x03, 0x80, /* 0000001110 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x38, 0x00, /* 0011100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 126 0x7e '~' */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x80, /* 0001100010 */
+	0x3d, 0x80, /* 0011110110 */
+	0x6f, 0x00, /* 0110111100 */
+	0x46, 0x00, /* 0100011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 127 0x7f '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x12, 0x00, /* 0001001000 */
+	0x21, 0x00, /* 0010000100 */
+	0x40, 0x80, /* 0100000010 */
+	0x40, 0x80, /* 0100000010 */
+	0x40, 0x80, /* 0100000010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 128 0x80 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x21, 0x80, /* 0010000110 */
+	0x40, 0x80, /* 0100000010 */
+	0x40, 0x00, /* 0100000000 */
+	0x40, 0x00, /* 0100000000 */
+	0x40, 0x00, /* 0100000000 */
+	0x40, 0x00, /* 0100000000 */
+	0x40, 0x00, /* 0100000000 */
+	0x40, 0x00, /* 0100000000 */
+	0x60, 0x80, /* 0110000010 */
+	0x31, 0x00, /* 0011000100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x08, 0x00, /* 0000100000 */
+	0x04, 0x00, /* 0000010000 */
+	0x02, 0x00, /* 0000001000 */
+	0x02, 0x00, /* 0000001000 */
+	0x1c, 0x00, /* 0001110000 */
+
+	/* 129 0x81 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7b, 0x80, /* 0111101110 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x3b, 0x00, /* 0011101100 */
+	0x1c, 0x80, /* 0001110010 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 130 0x82 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x01, 0x00, /* 0000000100 */
+	0x02, 0x00, /* 0000001000 */
+	0x04, 0x00, /* 0000010000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x19, 0x80, /* 0001100110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 131 0x83 '.' */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x31, 0x80, /* 0011000110 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x07, 0x80, /* 0000011110 */
+	0x39, 0x80, /* 0011100110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0xc0, /* 0011110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 132 0x84 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x07, 0x80, /* 0000011110 */
+	0x39, 0x80, /* 0011100110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0xc0, /* 0011110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 133 0x85 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x07, 0x80, /* 0000011110 */
+	0x39, 0x80, /* 0011100110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0xc0, /* 0011110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 134 0x86 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x07, 0x80, /* 0000011110 */
+	0x39, 0x80, /* 0011100110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0xc0, /* 0011110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 135 0x87 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x20, 0x80, /* 0010000010 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x70, 0x80, /* 0111000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x1f, 0x00, /* 0001111100 */
+	0x04, 0x00, /* 0000010000 */
+	0x02, 0x00, /* 0000001000 */
+	0x01, 0x00, /* 0000000100 */
+	0x0e, 0x00, /* 0000111000 */
+
+	/* 136 0x88 '.' */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x31, 0x80, /* 0011000110 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x19, 0x80, /* 0001100110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 137 0x89 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x19, 0x80, /* 0001100110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 138 0x8a '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x19, 0x80, /* 0001100110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 139 0x8b '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x36, 0x00, /* 0011011000 */
+	0x36, 0x00, /* 0011011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 140 0x8c '.' */
+	0x08, 0x00, /* 0000100000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x63, 0x00, /* 0110001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 141 0x8d '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 142 0x8e '.' */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x04, 0x00, /* 0000010000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x19, 0x00, /* 0001100100 */
+	0x19, 0x00, /* 0001100100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 143 0x8f '.' */
+	0x04, 0x00, /* 0000010000 */
+	0x0a, 0x00, /* 0000101000 */
+	0x0a, 0x00, /* 0000101000 */
+	0x04, 0x00, /* 0000010000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x19, 0x00, /* 0001100100 */
+	0x19, 0x00, /* 0001100100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 144 0x90 '.' */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x00, /* 0011000000 */
+	0x31, 0x00, /* 0011000100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x31, 0x00, /* 0011000100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x80, /* 0011000010 */
+	0x30, 0x80, /* 0011000010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 145 0x91 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3b, 0x80, /* 0011101110 */
+	0x6c, 0xc0, /* 0110110011 */
+	0x4c, 0xc0, /* 0100110011 */
+	0x0c, 0xc0, /* 0000110011 */
+	0x3f, 0xc0, /* 0011111111 */
+	0x6c, 0x00, /* 0110110000 */
+	0xcc, 0x00, /* 1100110000 */
+	0xcc, 0x00, /* 1100110000 */
+	0xee, 0xc0, /* 1110111011 */
+	0x7b, 0x80, /* 0111101110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 146 0x92 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x07, 0xc0, /* 0000011111 */
+	0x0e, 0x40, /* 0000111001 */
+	0x0e, 0x40, /* 0000111001 */
+	0x0e, 0x00, /* 0000111000 */
+	0x16, 0x00, /* 0001011000 */
+	0x16, 0x80, /* 0001011010 */
+	0x17, 0x80, /* 0001011110 */
+	0x16, 0x80, /* 0001011010 */
+	0x3e, 0x00, /* 0011111000 */
+	0x26, 0x00, /* 0010011000 */
+	0x26, 0x00, /* 0010011000 */
+	0x46, 0x40, /* 0100011001 */
+	0x46, 0x40, /* 0100011001 */
+	0xef, 0xc0, /* 1110111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 147 0x93 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x08, 0x00, /* 0000100000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xe1, 0x80, /* 1110000110 */
+	0x73, 0x00, /* 0111001100 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 148 0x94 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xe1, 0x80, /* 1110000110 */
+	0x73, 0x00, /* 0111001100 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 149 0x95 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x06, 0x00, /* 0000011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xe1, 0x80, /* 1110000110 */
+	0x73, 0x00, /* 0111001100 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 150 0x96 '.' */
+	0x08, 0x00, /* 0000100000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x63, 0x00, /* 0110001100 */
+	0x00, 0x00, /* 0000000000 */
+	0xf7, 0x80, /* 1111011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x77, 0x00, /* 0111011100 */
+	0x3d, 0x80, /* 0011110110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 151 0x97 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf7, 0x80, /* 1111011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x77, 0x00, /* 0111011100 */
+	0x3d, 0x80, /* 0011110110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 152 0x98 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x78, 0x00, /* 0111100000 */
+	0x70, 0x00, /* 0111000000 */
+
+	/* 153 0x99 '.' */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x17, 0x00, /* 0001011100 */
+	0x23, 0x00, /* 0010001100 */
+	0x21, 0x80, /* 0010000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x21, 0x00, /* 0010000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x1a, 0x00, /* 0001101000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 154 0x9a '.' */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0xf1, 0xc0, /* 1111000111 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x60, 0x80, /* 0110000010 */
+	0x71, 0x00, /* 0111000100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 155 0x9b '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x1f, 0x80, /* 0001111110 */
+	0x36, 0x80, /* 0011011010 */
+	0x26, 0x00, /* 0010011000 */
+	0x66, 0x00, /* 0110011000 */
+	0x66, 0x00, /* 0110011000 */
+	0x66, 0x00, /* 0110011000 */
+	0x66, 0x00, /* 0110011000 */
+	0x76, 0x00, /* 0111011000 */
+	0x36, 0x80, /* 0011011010 */
+	0x1f, 0x80, /* 0001111110 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 156 0x9c '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3b, 0x00, /* 0011101100 */
+	0x33, 0x00, /* 0011001100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x7e, 0x00, /* 0111111000 */
+	0x7e, 0x00, /* 0111111000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x7c, 0x80, /* 0111110010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x43, 0x00, /* 0100001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 157 0x9d '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x40, 0x80, /* 0100000010 */
+	0x40, 0x80, /* 0100000010 */
+	0x21, 0x00, /* 0010000100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 158 0x9e '.' */
+	0x00, 0x00, /* 0000000000 */
+	0xbf, 0x00, /* 1011111100 */
+	0x40, 0x80, /* 0100000010 */
+	0x40, 0x80, /* 0100000010 */
+	0x7f, 0x00, /* 0111111100 */
+	0x40, 0x00, /* 0100000000 */
+	0x48, 0x00, /* 0100100000 */
+	0x48, 0x00, /* 0100100000 */
+	0x5e, 0x00, /* 0101111000 */
+	0x48, 0x00, /* 0100100000 */
+	0x48, 0x00, /* 0100100000 */
+	0x48, 0x00, /* 0100100000 */
+	0x48, 0x80, /* 0100100010 */
+	0x47, 0x00, /* 0100011100 */
+	0xe0, 0x00, /* 1110000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 159 0x9f '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x00, /* 0000001100 */
+	0x04, 0x80, /* 0000010010 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x09, 0x00, /* 0000100100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x48, 0x00, /* 0100100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x08, 0x00, /* 0000100000 */
+	0x90, 0x00, /* 1001000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 160 0xa0 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x21, 0x80, /* 0010000110 */
+	0x07, 0x80, /* 0000011110 */
+	0x39, 0x80, /* 0011100110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x3d, 0xc0, /* 0011110111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 161 0xa1 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x00, /* 0000001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 162 0xa2 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xc1, 0x80, /* 1100000110 */
+	0xe1, 0x80, /* 1110000110 */
+	0x73, 0x00, /* 0111001100 */
+	0x3c, 0x00, /* 0011110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 163 0xa3 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0xf7, 0x80, /* 1111011110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x77, 0x00, /* 0111011100 */
+	0x3d, 0x80, /* 0011110110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 164 0xa4 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x38, 0x80, /* 0011100010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x47, 0x00, /* 0100011100 */
+	0x00, 0x00, /* 0000000000 */
+	0x6f, 0x00, /* 0110111100 */
+	0x7b, 0x80, /* 0111101110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x7b, 0xc0, /* 0111101111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 165 0xa5 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x38, 0x80, /* 0011100010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x47, 0x00, /* 0100011100 */
+	0x00, 0x00, /* 0000000000 */
+	0xe3, 0xc0, /* 1110001111 */
+	0x71, 0x80, /* 0111000110 */
+	0x79, 0x80, /* 0111100110 */
+	0x79, 0x80, /* 0111100110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x67, 0x80, /* 0110011110 */
+	0x63, 0x80, /* 0110001110 */
+	0x61, 0x80, /* 0110000110 */
+	0xf0, 0xc0, /* 1111000011 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 166 0xa6 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x63, 0x00, /* 0110001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x0f, 0x00, /* 0000111100 */
+	0x33, 0x00, /* 0011001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x67, 0x00, /* 0110011100 */
+	0x3b, 0x80, /* 0011101110 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 167 0xa7 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x21, 0x80, /* 0010000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x00, /* 0110000100 */
+	0x33, 0x00, /* 0011001100 */
+	0x1c, 0x00, /* 0001110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 168 0xa8 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x00, 0x00, /* 0000000000 */
+	0x06, 0x00, /* 0000011000 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x80, /* 0110000010 */
+	0x73, 0x80, /* 0111001110 */
+	0x3f, 0x00, /* 0011111100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 169 0xa9 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 170 0xaa '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 171 0xab '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x20, 0x00, /* 0010000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x20, 0x00, /* 0010000000 */
+	0x20, 0x80, /* 0010000010 */
+	0x21, 0x00, /* 0010000100 */
+	0x22, 0x00, /* 0010001000 */
+	0x74, 0x00, /* 0111010000 */
+	0x08, 0x00, /* 0000100000 */
+	0x17, 0x00, /* 0001011100 */
+	0x28, 0x80, /* 0010100010 */
+	0x43, 0x00, /* 0100001100 */
+	0x04, 0x00, /* 0000010000 */
+	0x08, 0x00, /* 0000100000 */
+	0x0f, 0x80, /* 0000111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 172 0xac '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x20, 0x00, /* 0010000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x20, 0x00, /* 0010000000 */
+	0x20, 0x80, /* 0010000010 */
+	0x21, 0x00, /* 0010000100 */
+	0x22, 0x00, /* 0010001000 */
+	0x74, 0x00, /* 0111010000 */
+	0x09, 0x00, /* 0000100100 */
+	0x13, 0x00, /* 0001001100 */
+	0x25, 0x00, /* 0010010100 */
+	0x49, 0x00, /* 0100100100 */
+	0x1f, 0x80, /* 0001111110 */
+	0x01, 0x00, /* 0000000100 */
+	0x01, 0x00, /* 0000000100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 173 0xad '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 174 0xae '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0d, 0x80, /* 0000110110 */
+	0x1b, 0x00, /* 0001101100 */
+	0x36, 0x00, /* 0011011000 */
+	0x6c, 0x00, /* 0110110000 */
+	0xd8, 0x00, /* 1101100000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x0d, 0x80, /* 0000110110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 175 0xaf '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x36, 0x00, /* 0011011000 */
+	0x1b, 0x00, /* 0001101100 */
+	0x0d, 0x80, /* 0000110110 */
+	0x06, 0xc0, /* 0000011011 */
+	0x0d, 0x80, /* 0000110110 */
+	0x1b, 0x00, /* 0001101100 */
+	0x36, 0x00, /* 0011011000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 176 0xb0 '.' */
+	0xc3, 0x00, /* 1100001100 */
+	0x41, 0x00, /* 0100000100 */
+	0x18, 0x40, /* 0001100001 */
+	0x10, 0x40, /* 0001000001 */
+	0xc3, 0x00, /* 1100001100 */
+	0x41, 0x00, /* 0100000100 */
+	0x18, 0x40, /* 0001100001 */
+	0x10, 0x40, /* 0001000001 */
+	0xc3, 0x00, /* 1100001100 */
+	0x41, 0x00, /* 0100000100 */
+	0x18, 0x40, /* 0001100001 */
+	0x10, 0x40, /* 0001000001 */
+	0xc3, 0x00, /* 1100001100 */
+	0x41, 0x00, /* 0100000100 */
+	0x18, 0x40, /* 0001100001 */
+	0x10, 0x40, /* 0001000001 */
+	0xc3, 0x00, /* 1100001100 */
+	0x41, 0x00, /* 0100000100 */
+
+	/* 177 0xb1 '.' */
+	0x11, 0x00, /* 0001000100 */
+	0xbb, 0x80, /* 1011101110 */
+	0x11, 0x00, /* 0001000100 */
+	0x44, 0x40, /* 0100010001 */
+	0xee, 0xc0, /* 1110111011 */
+	0x44, 0x40, /* 0100010001 */
+	0x11, 0x00, /* 0001000100 */
+	0xbb, 0x80, /* 1011101110 */
+	0x11, 0x00, /* 0001000100 */
+	0x44, 0x40, /* 0100010001 */
+	0xee, 0xc0, /* 1110111011 */
+	0x44, 0x40, /* 0100010001 */
+	0x11, 0x00, /* 0001000100 */
+	0xbb, 0x80, /* 1011101110 */
+	0x11, 0x00, /* 0001000100 */
+	0x44, 0x40, /* 0100010001 */
+	0xee, 0xc0, /* 1110111011 */
+	0x44, 0x40, /* 0100010001 */
+
+	/* 178 0xb2 '.' */
+	0x3c, 0xc0, /* 0011110011 */
+	0xbe, 0xc0, /* 1011111011 */
+	0xe7, 0x80, /* 1110011110 */
+	0xef, 0x80, /* 1110111110 */
+	0x3c, 0xc0, /* 0011110011 */
+	0xbe, 0xc0, /* 1011111011 */
+	0xe7, 0x80, /* 1110011110 */
+	0xef, 0x80, /* 1110111110 */
+	0x3c, 0xc0, /* 0011110011 */
+	0xbe, 0xc0, /* 1011111011 */
+	0xe7, 0x80, /* 1110011110 */
+	0xef, 0x80, /* 1110111110 */
+	0x3c, 0xc0, /* 0011110011 */
+	0xbe, 0xc0, /* 1011111011 */
+	0xe7, 0x80, /* 1110011110 */
+	0xef, 0x80, /* 1110111110 */
+	0x3c, 0xc0, /* 0011110011 */
+	0xbe, 0xc0, /* 1011111011 */
+
+	/* 179 0xb3 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 180 0xb4 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 181 0xb5 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 182 0xb6 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 183 0xb7 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0x00, /* 1111111100 */
+	0xff, 0x00, /* 1111111100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 184 0xb8 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 185 0xb9 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0x03, 0x00, /* 0000001100 */
+	0xfb, 0x00, /* 1111101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 186 0xba '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 187 0xbb '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0x00, /* 1111111100 */
+	0xff, 0x00, /* 1111111100 */
+	0x03, 0x00, /* 0000001100 */
+	0xfb, 0x00, /* 1111101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 188 0xbc '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0xfb, 0x00, /* 1111101100 */
+	0x03, 0x00, /* 0000001100 */
+	0xff, 0x00, /* 1111111100 */
+	0xff, 0x00, /* 1111111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 189 0xbd '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xff, 0x00, /* 1111111100 */
+	0xff, 0x00, /* 1111111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 190 0xbe '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 191 0xbf '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 192 0xc0 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 193 0xc1 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 194 0xc2 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 195 0xc3 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 196 0xc4 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 197 0xc5 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 198 0xc6 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 199 0xc7 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 200 0xc8 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x18, 0x00, /* 0001100000 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 201 0xc9 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x18, 0x00, /* 0001100000 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 202 0xca '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xfb, 0xc0, /* 1111101111 */
+	0xfb, 0xc0, /* 1111101111 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 203 0xcb '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0xfb, 0xc0, /* 1111101111 */
+	0xfb, 0xc0, /* 1111101111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 204 0xcc '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x18, 0x00, /* 0001100000 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0xc0, /* 0001101111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 205 0xcd '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 206 0xce '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xfb, 0xc0, /* 1111101111 */
+	0xfb, 0xc0, /* 1111101111 */
+	0x00, 0x00, /* 0000000000 */
+	0xfb, 0xc0, /* 1111101111 */
+	0xfb, 0xc0, /* 1111101111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 207 0xcf '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 208 0xd0 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 209 0xd1 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 210 0xd2 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 211 0xd3 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 212 0xd4 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 213 0xd5 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 214 0xd6 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 215 0xd7 '.' */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+	0x1b, 0x00, /* 0001101100 */
+
+	/* 216 0xd8 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 217 0xd9 '.' */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0xfc, 0x00, /* 1111110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 218 0xda '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+
+	/* 219 0xdb '.' */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+
+	/* 220 0xdc '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+
+	/* 221 0xdd '.' */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+	0xf8, 0x00, /* 1111100000 */
+
+	/* 222 0xde '.' */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+	0x07, 0xc0, /* 0000011111 */
+
+	/* 223 0xdf '.' */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0xff, 0xc0, /* 1111111111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 224 0xe0 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1c, 0x80, /* 0001110010 */
+	0x35, 0x80, /* 0011010110 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x63, 0x00, /* 0110001100 */
+	0x37, 0x80, /* 0011011110 */
+	0x1c, 0x80, /* 0001110010 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 225 0xe1 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x6f, 0x00, /* 0110111100 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x63, 0x00, /* 0110001100 */
+	0x6e, 0x00, /* 0110111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 226 0xe2 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 227 0xe3 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 228 0xe4 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0x80, /* 1111111110 */
+	0x60, 0x00, /* 0110000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x80, /* 0011000010 */
+	0x61, 0x80, /* 0110000110 */
+	0xff, 0x80, /* 1111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 229 0xe5 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1f, 0xc0, /* 0001111111 */
+	0x36, 0x00, /* 0011011000 */
+	0x63, 0x00, /* 0110001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x3e, 0x00, /* 0011111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 230 0xe6 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x73, 0x80, /* 0111001110 */
+	0x6d, 0x80, /* 0110110110 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0xc0, 0x00, /* 1100000000 */
+
+	/* 231 0xe7 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x01, 0x80, /* 0000000110 */
+	0x36, 0x40, /* 0011011001 */
+	0x5e, 0x00, /* 0101111000 */
+	0x8c, 0x00, /* 1000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 232 0xe8 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 233 0xe9 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x1f, 0x00, /* 0001111100 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x60, 0xc0, /* 0110000011 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x7f, 0xc0, /* 0111111111 */
+	0x60, 0xc0, /* 0110000011 */
+	0x31, 0x80, /* 0011000110 */
+	0x31, 0x80, /* 0011000110 */
+	0x1f, 0x00, /* 0001111100 */
+	0x0e, 0x00, /* 0000111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 234 0xea '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xc0, 0xc0, /* 1100000011 */
+	0xc0, 0xc0, /* 1100000011 */
+	0x61, 0x80, /* 0110000110 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0xf3, 0xc0, /* 1111001111 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 235 0xeb '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x07, 0x00, /* 0000011100 */
+	0x1f, 0x80, /* 0001111110 */
+	0x30, 0xc0, /* 0011000011 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x3e, 0x00, /* 0011111000 */
+	0x66, 0x00, /* 0110011000 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc3, 0x00, /* 1100001100 */
+	0xc3, 0x00, /* 1100001100 */
+	0x66, 0x00, /* 0110011000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 236 0xec '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x33, 0x00, /* 0011001100 */
+	0x6d, 0x80, /* 0110110110 */
+	0xcc, 0xc0, /* 1100110011 */
+	0xcc, 0xc0, /* 1100110011 */
+	0xcc, 0xc0, /* 1100110011 */
+	0xcc, 0xc0, /* 1100110011 */
+	0x6d, 0x80, /* 0110110110 */
+	0x33, 0x00, /* 0011001100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 237 0xed '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x01, 0x80, /* 0000000110 */
+	0x01, 0x80, /* 0000000110 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x37, 0x00, /* 0011011100 */
+	0x6d, 0x80, /* 0110110110 */
+	0xcc, 0xc0, /* 1100110011 */
+	0xcc, 0xc0, /* 1100110011 */
+	0xcc, 0xc0, /* 1100110011 */
+	0xcc, 0xc0, /* 1100110011 */
+	0x6d, 0x80, /* 0110110110 */
+	0x3b, 0x00, /* 0011101100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x60, 0x00, /* 0110000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 238 0xee '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x80, /* 0000001110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x3f, 0x80, /* 0011111110 */
+	0x3f, 0x80, /* 0011111110 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x18, 0x00, /* 0001100000 */
+	0x18, 0x00, /* 0001100000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x03, 0x80, /* 0000001110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 239 0xef '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x61, 0x80, /* 0110000110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 240 0xf0 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 241 0xf1 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 242 0xf2 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xe0, 0x00, /* 1110000000 */
+	0x38, 0x00, /* 0011100000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x03, 0x80, /* 0000001110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x38, 0x00, /* 0011100000 */
+	0xe0, 0x00, /* 1110000000 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0x00, /* 1111111100 */
+	0xff, 0x00, /* 1111111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 243 0xf3 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x03, 0x80, /* 0000001110 */
+	0x0e, 0x00, /* 0000111000 */
+	0x38, 0x00, /* 0011100000 */
+	0xe0, 0x00, /* 1110000000 */
+	0x38, 0x00, /* 0011100000 */
+	0x0e, 0x00, /* 0000111000 */
+	0x03, 0x80, /* 0000001110 */
+	0x00, 0x00, /* 0000000000 */
+	0xff, 0x80, /* 1111111110 */
+	0xff, 0x80, /* 1111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 244 0xf4 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x30, 0x00, /* 0011000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 245 0xf5 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x03, 0x00, /* 0000001100 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 246 0xf6 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 247 0xf7 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x38, 0x00, /* 0011100000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x06, 0xc0, /* 0000011011 */
+	0x03, 0x80, /* 0000001110 */
+	0x38, 0x00, /* 0011100000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x06, 0xc0, /* 0000011011 */
+	0x03, 0x80, /* 0000001110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 248 0xf8 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x33, 0x00, /* 0011001100 */
+	0x33, 0x00, /* 0011001100 */
+	0x1e, 0x00, /* 0001111000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 249 0xf9 '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 250 0xfa '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 251 0xfb '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0f, 0xc0, /* 0000111111 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0xcc, 0x00, /* 1100110000 */
+	0x6c, 0x00, /* 0110110000 */
+	0x3c, 0x00, /* 0011110000 */
+	0x1c, 0x00, /* 0001110000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 252 0xfc '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x27, 0x00, /* 0010011100 */
+	0x7b, 0x00, /* 0111101100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x31, 0x00, /* 0011000100 */
+	0x7b, 0x80, /* 0111101110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 253 0xfd '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x1e, 0x00, /* 0001111000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x63, 0x00, /* 0110001100 */
+	0x43, 0x00, /* 0100001100 */
+	0x06, 0x00, /* 0000011000 */
+	0x0c, 0x00, /* 0000110000 */
+	0x18, 0x00, /* 0001100000 */
+	0x30, 0x80, /* 0011000010 */
+	0x7f, 0x80, /* 0111111110 */
+	0x7f, 0x80, /* 0111111110 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 254 0xfe '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x3f, 0x00, /* 0011111100 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+	/* 255 0xff '.' */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+	0x00, 0x00, /* 0000000000 */
+
+};
+
+
+struct font_desc font_10x18 = {
+	FONT10x18_IDX,
+	"10x18",
+	10,
+	18,
+	fontdata_10x18,
+#ifdef __sparc__
+	5
+#else
+	-1
+#endif
+};
diff --git a/drivers/video/console/font_7x14.c b/drivers/video/console/font_7x14.c
new file mode 100644
index 0000000..1fa7fcf
--- /dev/null
+++ b/drivers/video/console/font_7x14.c
@@ -0,0 +1,4118 @@
+/**************************************/
+/* this file adapted from font_8x16.c */
+/* by Jurriaan Kalkman 05-2005        */
+/**************************************/
+
+#include <linux/font.h>
+
+#define FONTDATAMAX 3584
+
+static unsigned char fontdata_7x14[FONTDATAMAX] = {
+
+	/* 0 0x00 '^@' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 1 0x01 '^A' */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0x82, /* 1000001 */
+	0xaa, /* 1010101 */
+	0x82, /* 1000001 */
+	0x82, /* 1000001 */
+	0xba, /* 1011101 */
+	0x92, /* 1001001 */
+	0x82, /* 1000001 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 2 0x02 '^B' */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0xfe, /* 1111111 */
+	0xd6, /* 1101011 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xc6, /* 1100011 */
+	0xee, /* 1110111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 3 0x03 '^C' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x7c, /* 0111110 */
+	0xfe, /* 1111111 */
+	0x7c, /* 0111110 */
+	0x38, /* 0011100 */
+	0x18, /* 0001100 */
+	0x10, /* 0001000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 4 0x04 '^D' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x7c, /* 0111110 */
+	0xfe, /* 1111111 */
+	0x7c, /* 0111110 */
+	0x38, /* 0011100 */
+	0x10, /* 0001000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 5 0x05 '^E' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x38, /* 0011100 */
+	0x38, /* 0011100 */
+	0xee, /* 1110111 */
+	0xee, /* 1110111 */
+	0xee, /* 1110111 */
+	0x10, /* 0001000 */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 6 0x06 '^F' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x7c, /* 0111110 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0x7c, /* 0111110 */
+	0x10, /* 0001000 */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 7 0x07 '^G' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 8 0x08 '^H' */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xe6, /* 1110011 */
+	0xc2, /* 1100001 */
+	0xc2, /* 1100001 */
+	0xe6, /* 1110011 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+
+	/* 9 0x09 '^I' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x44, /* 0100010 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 10 0x0a '^J' */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xc6, /* 1100011 */
+	0x92, /* 1001001 */
+	0xba, /* 1011101 */
+	0x92, /* 1001001 */
+	0xc6, /* 1100011 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+
+	/* 11 0x0b '^K' */
+	0x00, /* 0000000 */
+	0x1e, /* 0001111 */
+	0x0e, /* 0000111 */
+	0x1a, /* 0001101 */
+	0x1a, /* 0001101 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 12 0x0c '^L' */
+	0x00, /* 0000000 */
+	0x3c, /* 0011110 */
+	0x66, /* 0110011 */
+	0x66, /* 0110011 */
+	0x66, /* 0110011 */
+	0x66, /* 0110011 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x7e, /* 0111111 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 13 0x0d '^M' */
+	0x00, /* 0000000 */
+	0x3e, /* 0011111 */
+	0x36, /* 0011011 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x70, /* 0111000 */
+	0xf0, /* 1111000 */
+	0xe0, /* 1110000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 14 0x0e '^N' */
+	0x00, /* 0000000 */
+	0x7e, /* 0111111 */
+	0x66, /* 0110011 */
+	0x7e, /* 0111111 */
+	0x66, /* 0110011 */
+	0x66, /* 0110011 */
+	0x66, /* 0110011 */
+	0x66, /* 0110011 */
+	0x6e, /* 0110111 */
+	0xee, /* 1110111 */
+	0xec, /* 1110110 */
+	0xc0, /* 1100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 15 0x0f '^O' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x10, /* 0001000 */
+	0x10, /* 0001000 */
+	0xd6, /* 1101011 */
+	0x38, /* 0011100 */
+	0xee, /* 1110111 */
+	0x38, /* 0011100 */
+	0xd6, /* 1101011 */
+	0x10, /* 0001000 */
+	0x10, /* 0001000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 16 0x10 '^P' */
+	0x00, /* 0000000 */
+	0x80, /* 1000000 */
+	0xc0, /* 1100000 */
+	0xe0, /* 1110000 */
+	0xf0, /* 1111000 */
+	0xfc, /* 1111110 */
+	0xf0, /* 1111000 */
+	0xe0, /* 1110000 */
+	0xc0, /* 1100000 */
+	0x80, /* 1000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 17 0x11 '^Q' */
+	0x00, /* 0000000 */
+	0x04, /* 0000010 */
+	0x0c, /* 0000110 */
+	0x1c, /* 0001110 */
+	0x3c, /* 0011110 */
+	0xfc, /* 1111110 */
+	0x3c, /* 0011110 */
+	0x1c, /* 0001110 */
+	0x0c, /* 0000110 */
+	0x04, /* 0000010 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 18 0x12 '^R' */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x7e, /* 0111111 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x7e, /* 0111111 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 19 0x13 '^S' */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 20 0x14 '^T' */
+	0x00, /* 0000000 */
+	0x7e, /* 0111111 */
+	0xd4, /* 1101010 */
+	0xd4, /* 1101010 */
+	0xd4, /* 1101010 */
+	0x74, /* 0111010 */
+	0x14, /* 0001010 */
+	0x14, /* 0001010 */
+	0x14, /* 0001010 */
+	0x14, /* 0001010 */
+	0x16, /* 0001011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 21 0x15 '^U' */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x60, /* 0110000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x18, /* 0001100 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 22 0x16 '^V' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 23 0x17 '^W' */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x7e, /* 0111111 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x7e, /* 0111111 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x7e, /* 0111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 24 0x18 '^X' */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x7e, /* 0111111 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 25 0x19 '^Y' */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x7e, /* 0111111 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 26 0x1a '^Z' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0xfc, /* 1111110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 27 0x1b '^[' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xfc, /* 1111110 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 28 0x1c '^\' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 29 0x1d '^]' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x28, /* 0010100 */
+	0x6c, /* 0110110 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x28, /* 0010100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 30 0x1e '^^' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 31 0x1f '^_' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 32 0x20 ' ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 33 0x21 '!' */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x3c, /* 0011110 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 34 0x22 '"' */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x28, /* 0010100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 35 0x23 '#' */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 36 0x24 '$' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xc4, /* 1100010 */
+	0xc0, /* 1100000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x8c, /* 1000110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+
+	/* 37 0x25 '%' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xc0, /* 1100000 */
+	0xc4, /* 1100010 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xcc, /* 1100110 */
+	0x8c, /* 1000110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 38 0x26 '&' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x78, /* 0111100 */
+	0xde, /* 1101111 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xdc, /* 1101110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 39 0x27 ''' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 40 0x28 '(' */
+	0x00, /* 0000000 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x0c, /* 0000110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 41 0x29 ')' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 42 0x2a '*' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0xfe, /* 1111111 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 43 0x2b '+' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x10, /* 0001000 */
+	0x10, /* 0001000 */
+	0x7c, /* 0111110 */
+	0x10, /* 0001000 */
+	0x10, /* 0001000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 44 0x2c ',' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 45 0x2d '-' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 46 0x2e '.' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 47 0x2f '/' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x04, /* 0000010 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0x80, /* 1000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 48 0x30 '0' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xdc, /* 1101110 */
+	0xec, /* 1110110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 49 0x31 '1' */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x38, /* 0011100 */
+	0x78, /* 0111100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 50 0x32 '2' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 51 0x33 '3' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x38, /* 0011100 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 52 0x34 '4' */
+	0x00, /* 0000000 */
+	0x0c, /* 0000110 */
+	0x1c, /* 0001110 */
+	0x3c, /* 0011110 */
+	0x6c, /* 0110110 */
+	0xcc, /* 1100110 */
+	0xfe, /* 1111111 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 53 0x35 '5' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xf8, /* 1111100 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 54 0x36 '6' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xf8, /* 1111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 55 0x37 '7' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 56 0x38 '8' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 57 0x39 '9' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x7c, /* 0111110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 58 0x3a ':' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 59 0x3b ';' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 60 0x3c '<' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x04, /* 0000010 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x0c, /* 0000110 */
+	0x04, /* 0000010 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 61 0x3d '=' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 62 0x3e '>' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x40, /* 0100000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x40, /* 0100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 63 0x3f '?' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 64 0x40 '@' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xdc, /* 1101110 */
+	0xdc, /* 1101110 */
+	0xd8, /* 1101100 */
+	0xc0, /* 1100000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 65 0x41 'A' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 66 0x42 'B' */
+	0x00, /* 0000000 */
+	0xf8, /* 1111100 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x78, /* 0111100 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xf8, /* 1111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 67 0x43 'C' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc4, /* 1100010 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc4, /* 1100010 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 68 0x44 'D' */
+	0x00, /* 0000000 */
+	0xf0, /* 1111000 */
+	0xd8, /* 1101100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xd8, /* 1101100 */
+	0xf0, /* 1111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 69 0x45 'E' */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0x6c, /* 0110110 */
+	0x64, /* 0110010 */
+	0x68, /* 0110100 */
+	0x78, /* 0111100 */
+	0x68, /* 0110100 */
+	0x60, /* 0110000 */
+	0x64, /* 0110010 */
+	0x6c, /* 0110110 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 70 0x46 'F' */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0x64, /* 0110010 */
+	0x60, /* 0110000 */
+	0x68, /* 0110100 */
+	0x78, /* 0111100 */
+	0x68, /* 0110100 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 71 0x47 'G' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc4, /* 1100010 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xdc, /* 1101110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x6c, /* 0110110 */
+	0x34, /* 0011010 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 72 0x48 'H' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 73 0x49 'I' */
+	0x00, /* 0000000 */
+	0x3c, /* 0011110 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 74 0x4a 'J' */
+	0x00, /* 0000000 */
+	0x1c, /* 0001110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 75 0x4b 'K' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xd8, /* 1101100 */
+	0xf0, /* 1111000 */
+	0xf0, /* 1111000 */
+	0xd8, /* 1101100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 76 0x4c 'L' */
+	0x00, /* 0000000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc4, /* 1100010 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 77 0x4d 'M' */
+	0x00, /* 0000000 */
+	0xc6, /* 1100011 */
+	0xee, /* 1110111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xd6, /* 1101011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 78 0x4e 'N' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xec, /* 1110110 */
+	0xec, /* 1110110 */
+	0xfc, /* 1111110 */
+	0xdc, /* 1101110 */
+	0xdc, /* 1101110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 79 0x4f 'O' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 80 0x50 'P' */
+	0x00, /* 0000000 */
+	0xf8, /* 1111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xf8, /* 1111100 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 81 0x51 'Q' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xdc, /* 1101110 */
+	0x78, /* 0111100 */
+	0x18, /* 0001100 */
+	0x1c, /* 0001110 */
+	0x00, /* 0000000 */
+
+	/* 82 0x52 'R' */
+	0x00, /* 0000000 */
+	0xf8, /* 1111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xf8, /* 1111100 */
+	0xd8, /* 1101100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 83 0x53 'S' */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0xc4, /* 1100010 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0x60, /* 0110000 */
+	0x38, /* 0011100 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x8c, /* 1000110 */
+	0xf8, /* 1111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 84 0x54 'T' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0xb4, /* 1011010 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 85 0x55 'U' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 86 0x56 'V' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 87 0x57 'W' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xfc, /* 1111110 */
+	0x48, /* 0100100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 88 0x58 'X' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 89 0x59 'Y' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 90 0x5a 'Z' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0x8c, /* 1000110 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc4, /* 1100010 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 91 0x5b '[' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 92 0x5c '\' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x80, /* 1000000 */
+	0xc0, /* 1100000 */
+	0xe0, /* 1110000 */
+	0x70, /* 0111000 */
+	0x38, /* 0011100 */
+	0x1c, /* 0001110 */
+	0x0c, /* 0000110 */
+	0x04, /* 0000010 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 93 0x5d ']' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 94 0x5e '^' */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc6, /* 1100011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 95 0x5f '_' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+
+	/* 96 0x60 '`' */
+	0x00, /* 0000000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 97 0x61 'a' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 98 0x62 'b' */
+	0x00, /* 0000000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xf0, /* 1111000 */
+	0xd8, /* 1101100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xf8, /* 1111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 99 0x63 'c' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 100 0x64 'd' */
+	0x00, /* 0000000 */
+	0x1c, /* 0001110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x3c, /* 0011110 */
+	0x6c, /* 0110110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 101 0x65 'e' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 102 0x66 'f' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x64, /* 0110010 */
+	0x60, /* 0110000 */
+	0xf0, /* 1111000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0xf0, /* 1111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 103 0x67 'g' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x76, /* 0111011 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x7c, /* 0111110 */
+	0x0c, /* 0000110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+
+	/* 104 0x68 'h' */
+	0x00, /* 0000000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xd8, /* 1101100 */
+	0xec, /* 1110110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 105 0x69 'i' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 106 0x6a 'j' */
+	0x00, /* 0000000 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x00, /* 0000000 */
+	0x1c, /* 0001110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+
+	/* 107 0x6b 'k' */
+	0x00, /* 0000000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0xd8, /* 1101100 */
+	0xf0, /* 1111000 */
+	0xf0, /* 1111000 */
+	0xd8, /* 1101100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 108 0x6c 'l' */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 109 0x6d 'm' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xec, /* 1110110 */
+	0xfe, /* 1111111 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 110 0x6e 'n' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xb8, /* 1011100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 111 0x6f 'o' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 112 0x70 'p' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xb8, /* 1011100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xf8, /* 1111100 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+
+	/* 113 0x71 'q' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x74, /* 0111010 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x7c, /* 0111110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+
+	/* 114 0x72 'r' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xb8, /* 1011100 */
+	0xec, /* 1110110 */
+	0xcc, /* 1100110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 115 0x73 's' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 116 0x74 't' */
+	0x00, /* 0000000 */
+	0x10, /* 0001000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x36, /* 0011011 */
+	0x1c, /* 0001110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 117 0x75 'u' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 118 0x76 'v' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 119 0x77 'w' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 120 0x78 'x' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 121 0x79 'y' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x7c, /* 0111110 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0xf0, /* 1111000 */
+
+	/* 122 0x7a 'z' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 123 0x7b '{' */
+	0x00, /* 0000000 */
+	0x1c, /* 0001110 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xe0, /* 1110000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x1c, /* 0001110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 124 0x7c '|' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 125 0x7d '}' */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x0e, /* 0000111 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 126 0x7e '~' */
+	0x00, /* 0000000 */
+	0xec, /* 1110110 */
+	0xb8, /* 1011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 127 0x7f '' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 128 0x80 '€' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc4, /* 1100010 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc4, /* 1100010 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x18, /* 0001100 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+
+	/* 129 0x81 '' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 130 0x82 '‚' */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 131 0x83 'ƒ' */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 132 0x84 '„' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 133 0x85 '…' */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 134 0x86 '†' */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 135 0x87 '‡' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xe0, /* 1110000 */
+
+	/* 136 0x88 'ˆ' */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 137 0x89 '‰' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 138 0x8a 'Š' */
+	0xc0, /* 1100000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 139 0x8b '‹' */
+	0x00, /* 0000000 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x3c, /* 0011110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 140 0x8c 'Œ' */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 141 0x8d '' */
+	0xc0, /* 1100000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 142 0x8e 'Ž' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 143 0x8f '' */
+	0x30, /* 0011000 */
+	0x48, /* 0100100 */
+	0x48, /* 0100100 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 144 0x90 '' */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xc4, /* 1100010 */
+	0xd0, /* 1101000 */
+	0xf0, /* 1111000 */
+	0xd0, /* 1101000 */
+	0xc4, /* 1100010 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 145 0x91 '‘' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xec, /* 1110110 */
+	0x36, /* 0011011 */
+	0x36, /* 0011011 */
+	0x7e, /* 0111111 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0x6e, /* 0110111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 146 0x92 '’' */
+	0x00, /* 0000000 */
+	0x3e, /* 0011111 */
+	0x6c, /* 0110110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xfe, /* 1111111 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xce, /* 1100111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 147 0x93 '“' */
+	0x10, /* 0001000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 148 0x94 '”' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 149 0x95 '•' */
+	0xc0, /* 1100000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 150 0x96 '–' */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 151 0x97 '—' */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 152 0x98 '˜' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x7c, /* 0111110 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x70, /* 0111000 */
+
+	/* 153 0x99 '™' */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 154 0x9a 'š' */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 155 0x9b '›' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0x7c, /* 0111110 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 156 0x9c 'œ' */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x64, /* 0110010 */
+	0x60, /* 0110000 */
+	0xf0, /* 1111000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0xe6, /* 1110011 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 157 0x9d '' */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 158 0x9e 'ž' */
+	0xf8, /* 1111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xf8, /* 1111100 */
+	0xc4, /* 1100010 */
+	0xcc, /* 1100110 */
+	0xde, /* 1101111 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xc6, /* 1100011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 159 0x9f 'Ÿ' */
+	0x1c, /* 0001110 */
+	0x36, /* 0011011 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xb0, /* 1011000 */
+	0xe0, /* 1110000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 160 0xa0 ' ' */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 161 0xa1 '¡' */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 162 0xa2 '¢' */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 163 0xa3 '£' */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 164 0xa4 '¤' */
+	0x00, /* 0000000 */
+	0x76, /* 0111011 */
+	0xdc, /* 1101110 */
+	0x00, /* 0000000 */
+	0xb8, /* 1011100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 165 0xa5 '¥' */
+	0x76, /* 0111011 */
+	0xdc, /* 1101110 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xec, /* 1110110 */
+	0xec, /* 1110110 */
+	0xfc, /* 1111110 */
+	0xdc, /* 1101110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 166 0xa6 '¦' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 167 0xa7 '§' */
+	0x00, /* 0000000 */
+	0x70, /* 0111000 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+	0xf8, /* 1111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 168 0xa8 '¨' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 169 0xa9 '©' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 170 0xaa 'ª' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 171 0xab '«' */
+	0x60, /* 0110000 */
+	0xe0, /* 1110000 */
+	0x62, /* 0110001 */
+	0x66, /* 0110011 */
+	0x6c, /* 0110110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0xb8, /* 1011100 */
+	0x4c, /* 0100110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x7c, /* 0111110 */
+
+	/* 172 0xac '¬' */
+	0x60, /* 0110000 */
+	0xe0, /* 1110000 */
+	0x62, /* 0110001 */
+	0x66, /* 0110011 */
+	0x6c, /* 0110110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x6c, /* 0110110 */
+	0xdc, /* 1101110 */
+	0xb4, /* 1011010 */
+	0x7e, /* 0111111 */
+	0x0c, /* 0000110 */
+	0x0c, /* 0000110 */
+	0x00, /* 0000000 */
+
+	/* 173 0xad '­' */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 174 0xae '®' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x36, /* 0011011 */
+	0x6c, /* 0110110 */
+	0xd8, /* 1101100 */
+	0x6c, /* 0110110 */
+	0x36, /* 0011011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 175 0xaf '¯' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xd8, /* 1101100 */
+	0x6c, /* 0110110 */
+	0x36, /* 0011011 */
+	0x6c, /* 0110110 */
+	0xd8, /* 1101100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 176 0xb0 '°' */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+	0x88, /* 1000100 */
+	0x22, /* 0010001 */
+
+	/* 177 0xb1 '±' */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+	0x54, /* 0101010 */
+	0xaa, /* 1010101 */
+
+	/* 178 0xb2 '²' */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+	0xee, /* 1110111 */
+	0xba, /* 1011101 */
+
+	/* 179 0xb3 '³' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 180 0xb4 '´' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 181 0xb5 'µ' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 182 0xb6 '¶' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xec, /* 1110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 183 0xb7 '·' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 184 0xb8 '¸' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 185 0xb9 '¹' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xec, /* 1110110 */
+	0x0c, /* 0000110 */
+	0xec, /* 1110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 186 0xba 'º' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 187 0xbb '»' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x0c, /* 0000110 */
+	0xec, /* 1110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 188 0xbc '¼' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xec, /* 1110110 */
+	0x0c, /* 0000110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 189 0xbd '½' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 190 0xbe '¾' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 191 0xbf '¿' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xf0, /* 1111000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 192 0xc0 'À' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 193 0xc1 'Á' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 194 0xc2 'Â' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 195 0xc3 'Ã' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 196 0xc4 'Ä' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 197 0xc5 'Å' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfe, /* 1111111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 198 0xc6 'Æ' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 199 0xc7 'Ç' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6e, /* 0110111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 200 0xc8 'È' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6e, /* 0110111 */
+	0x60, /* 0110000 */
+	0x7e, /* 0111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 201 0xc9 'É' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7e, /* 0111111 */
+	0x60, /* 0110000 */
+	0x6e, /* 0110111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 202 0xca 'Ê' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xee, /* 1110111 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 203 0xcb 'Ë' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0xee, /* 1110111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 204 0xcc 'Ì' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6e, /* 0110111 */
+	0x60, /* 0110000 */
+	0x6e, /* 0110111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 205 0xcd 'Í' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 206 0xce 'Î' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xee, /* 1110111 */
+	0x00, /* 0000000 */
+	0xee, /* 1110111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 207 0xcf 'Ï' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 208 0xd0 'Ð' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 209 0xd1 'Ñ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 210 0xd2 'Ò' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 211 0xd3 'Ó' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x7e, /* 0111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 212 0xd4 'Ô' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 213 0xd5 'Õ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 214 0xd6 'Ö' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7e, /* 0111111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 215 0xd7 '×' */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+
+	/* 216 0xd8 'Ø' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfe, /* 1111111 */
+	0x30, /* 0011000 */
+	0xfe, /* 1111111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 217 0xd9 'Ù' */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xf0, /* 1111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 218 0xda 'Ú' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x3e, /* 0011111 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 219 0xdb 'Û' */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+
+	/* 220 0xdc 'Ü' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+
+	/* 221 0xdd 'Ý' */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+	0xe0, /* 1110000 */
+
+	/* 222 0xde 'Þ' */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+	0x1e, /* 0001111 */
+
+	/* 223 0xdf 'ß' */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 224 0xe0 'à' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x76, /* 0111011 */
+	0xdc, /* 1101110 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xdc, /* 1101110 */
+	0x76, /* 0111011 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 225 0xe1 'á' */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xd8, /* 1101100 */
+	0xcc, /* 1100110 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 226 0xe2 'â' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 227 0xe3 'ã' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfe, /* 1111111 */
+	0xfe, /* 1111111 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 228 0xe4 'ä' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 229 0xe5 'å' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7e, /* 0111111 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 230 0xe6 'æ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xf8, /* 1111100 */
+	0xc0, /* 1100000 */
+	0xc0, /* 1100000 */
+	0x80, /* 1000000 */
+
+	/* 231 0xe7 'ç' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x76, /* 0111011 */
+	0xdc, /* 1101110 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 232 0xe8 'è' */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x30, /* 0011000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 233 0xe9 'é' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xfc, /* 1111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 234 0xea 'ê' */
+	0x00, /* 0000000 */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0xc6, /* 1100011 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0xee, /* 1110111 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 235 0xeb 'ë' */
+	0x00, /* 0000000 */
+	0x3c, /* 0011110 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x7c, /* 0111110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x78, /* 0111100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 236 0xec 'ì' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 237 0xed 'í' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x06, /* 0000011 */
+	0x0c, /* 0000110 */
+	0x7c, /* 0111110 */
+	0xd6, /* 1101011 */
+	0xd6, /* 1101011 */
+	0xe6, /* 1110011 */
+	0x7c, /* 0111110 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 238 0xee 'î' */
+	0x00, /* 0000000 */
+	0x1c, /* 0001110 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x7c, /* 0111110 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x1c, /* 0001110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 239 0xef 'ï' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0xcc, /* 1100110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 240 0xf0 'ð' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 241 0xf1 'ñ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0xfc, /* 1111110 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 242 0xf2 'ò' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x0c, /* 0000110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 243 0xf3 'ó' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x60, /* 0110000 */
+	0xc0, /* 1100000 */
+	0x60, /* 0110000 */
+	0x30, /* 0011000 */
+	0x18, /* 0001100 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 244 0xf4 'ô' */
+	0x00, /* 0000000 */
+	0x1c, /* 0001110 */
+	0x36, /* 0011011 */
+	0x36, /* 0011011 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+
+	/* 245 0xf5 'õ' */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0x70, /* 0111000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 246 0xf6 'ö' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 247 0xf7 '÷' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x76, /* 0111011 */
+	0xdc, /* 1101110 */
+	0x00, /* 0000000 */
+	0x76, /* 0111011 */
+	0xdc, /* 1101110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 248 0xf8 'ø' */
+	0x38, /* 0011100 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 249 0xf9 'ù' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 250 0xfa 'ú' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x30, /* 0011000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 251 0xfb 'û' */
+	0x1e, /* 0001111 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0x18, /* 0001100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0xd8, /* 1101100 */
+	0x78, /* 0111100 */
+	0x38, /* 0011100 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 252 0xfc 'ü' */
+	0xd8, /* 1101100 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x6c, /* 0110110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 253 0xfd 'ý' */
+	0x78, /* 0111100 */
+	0xcc, /* 1100110 */
+	0x18, /* 0001100 */
+	0x30, /* 0011000 */
+	0x64, /* 0110010 */
+	0xfc, /* 1111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 254 0xfe 'þ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x7c, /* 0111110 */
+	0x7c, /* 0111110 */
+	0x7c, /* 0111110 */
+	0x7c, /* 0111110 */
+	0x7c, /* 0111110 */
+	0x7c, /* 0111110 */
+	0x7c, /* 0111110 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+	/* 255 0xff 'ÿ' */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+	0x00, /* 0000000 */
+
+};
+
+
+struct font_desc font_7x14 = {
+	FONT7x14_IDX,
+	"7x14",
+	7,
+	14,
+	fontdata_7x14,
+	0
+};
diff --git a/drivers/video/console/font_sun12x22.c b/drivers/video/console/font_sun12x22.c
index 05215d0..c7bd967 100644
--- a/drivers/video/console/font_sun12x22.c
+++ b/drivers/video/console/font_sun12x22.c
@@ -29,24 +29,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 1 0x01 '^A' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x30, 0x60, /* 001100000110 */
+	0x65, 0x30, /* 011001010011 */
+	0x6d, 0xb0, /* 011011011011 */
+	0x60, 0x30, /* 011000000011 */
+	0x62, 0x30, /* 011000100011 */
+	0x62, 0x30, /* 011000100011 */
+	0x60, 0x30, /* 011000000011 */
+	0x6f, 0xb0, /* 011011111011 */
+	0x67, 0x30, /* 011001110011 */
+	0x30, 0x60, /* 001100000110 */
+	0x1f, 0xc0, /* 000111111100 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -54,24 +53,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 2 0x02 '^B' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x7a, 0xf0, /* 011110101111 */
+	0x72, 0x70, /* 011100100111 */
+	0x7f, 0xf0, /* 011111111111 */
+	0x7d, 0xf0, /* 011111011111 */
+	0x7d, 0xf0, /* 011111011111 */
+	0x7f, 0xf0, /* 011111111111 */
+	0x70, 0x70, /* 011100000111 */
+	0x78, 0xf0, /* 011110001111 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x1f, 0xc0, /* 000111111100 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -79,24 +77,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 3 0x03 '^C' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x19, 0x80, /* 000110011000 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x3f, 0xc0, /* 001111111100 */
 	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x1f, 0x80, /* 000111111000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x06, 0x00, /* 000001100000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -104,49 +101,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 4 0x04 '^D' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x02, 0x00, /* 000000100000 */
+	0x07, 0x00, /* 000001110000 */
+	0x0f, 0x80, /* 000011111000 */
+	0x0f, 0x80, /* 000011111000 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x0f, 0x80, /* 000011111000 */
+	0x0f, 0x80, /* 000011111000 */
+	0x07, 0x00, /* 000001110000 */
+	0x02, 0x00, /* 000000100000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 5 0x05 '^E' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x02, 0x00, /* 000000100000 */
+	0x07, 0x00, /* 000001110000 */
+	0x07, 0x00, /* 000001110000 */
+	0x02, 0x00, /* 000000100000 */
+	0x18, 0xc0, /* 000110001100 */
+	0x3d, 0xe0, /* 001111011110 */
+	0x3d, 0xe0, /* 001111011110 */
+	0x1a, 0xc0, /* 000110101100 */
+	0x02, 0x00, /* 000000100000 */
+	0x07, 0x00, /* 000001110000 */
+	0x0f, 0x80, /* 000011111000 */
+	0x1f, 0xc0, /* 000111111100 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -154,23 +149,22 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 6 0x06 '^F' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x1f, 0x80, /* 000111111000 */
 	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x36, 0xc0, /* 001101101100 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x1f, 0x80, /* 000111111000 */
 	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -179,24 +173,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 7 0x07 '^G' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x1f, 0x80, /* 000111111000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x06, 0x00, /* 000001100000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -204,49 +197,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 8 0x08 '^H' */
-	/* FIXME */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xf9, 0xf0, /* 111110011111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xe0, 0x70, /* 111000000111 */
+	0xe0, 0x70, /* 111000000111 */
+	0xc0, 0x30, /* 110000000011 */
+	0xc0, 0x30, /* 110000000011 */
+	0xe0, 0x70, /* 111000000111 */
+	0xe0, 0x70, /* 111000000111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xf9, 0xf0, /* 111110011111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
 
 	/* 9 0x09 '^I' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x06, 0x00, /* 000001100000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -254,149 +245,143 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 10 0x0a '^J' */
-	/* FIXME */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xf9, 0xf0, /* 111110011111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xe6, 0x70, /* 111001100111 */
+	0xe6, 0x70, /* 111001100111 */
+	0xcf, 0x30, /* 110011110011 */
+	0xcf, 0x30, /* 110011110011 */
+	0xe6, 0x70, /* 111001100111 */
+	0xe6, 0x70, /* 111001100111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xf0, 0xf0, /* 111100001111 */
+	0xf9, 0xf0, /* 111110011111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
 
 	/* 11 0x0b '^K' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x01, 0xe0, /* 000000011110 */
+	0x03, 0x60, /* 000000110110 */
+	0x06, 0x60, /* 000001100110 */
+	0x1e, 0x00, /* 000111100000 */
+	0x33, 0x00, /* 001100110000 */
+	0x33, 0x00, /* 001100110000 */
+	0x61, 0x80, /* 011000011000 */
+	0x61, 0x80, /* 011000011000 */
+	0x33, 0x00, /* 001100110000 */
+	0x33, 0x00, /* 001100110000 */
+	0x1e, 0x00, /* 000111100000 */
+	0x0c, 0x00, /* 000011000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 12 0x0c '^L' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x19, 0x80, /* 000110011000 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x19, 0x80, /* 000110011000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 13 0x0d '^M' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x0c, 0x60, /* 000011000110 */
+	0x0c, 0x60, /* 000011000110 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x3c, 0x00, /* 001111000000 */
+	0x7c, 0x00, /* 011111000000 */
+	0x78, 0x00, /* 011110000000 */
+	0x30, 0x00, /* 001100000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 14 0x0e '^N' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x1f, 0xe0, /* 000111111110 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x60, /* 000110000110 */
+	0x1f, 0xe0, /* 000111111110 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x60, /* 000110000110 */
+	0x19, 0xe0, /* 000110011110 */
+	0x1b, 0xe0, /* 000110111110 */
+	0x1b, 0xc0, /* 000110111100 */
+	0x79, 0x80, /* 011110011000 */
+	0xf8, 0x00, /* 111110000000 */
+	0xf0, 0x00, /* 111100000000 */
+	0x60, 0x00, /* 011000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 15 0x0f '^O' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x18, 0xc0, /* 000110001100 */
+	0x0d, 0x80, /* 000011011000 */
+	0x6d, 0xb0, /* 011011011011 */
+	0x3d, 0xe0, /* 001111011110 */
+	0x00, 0x00, /* 000000000000 */
+	0x3d, 0xe0, /* 001111011110 */
+	0x6d, 0xb0, /* 011011011011 */
+	0x0d, 0x80, /* 000011011000 */
+	0x18, 0xc0, /* 000110001100 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -404,74 +389,71 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 16 0x10 '^P' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x00, 0x20, /* 000000000010 */
+	0x00, 0x60, /* 000000000110 */
+	0x00, 0xe0, /* 000000001110 */
+	0x01, 0xe0, /* 000000011110 */
+	0x03, 0xe0, /* 000000111110 */
+	0x07, 0xe0, /* 000001111110 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x1f, 0xe0, /* 000111111110 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x1f, 0xe0, /* 000111111110 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x07, 0xe0, /* 000001111110 */
+	0x03, 0xe0, /* 000000111110 */
+	0x01, 0xe0, /* 000000011110 */
+	0x00, 0xe0, /* 000000001110 */
+	0x00, 0x60, /* 000000000110 */
+	0x00, 0x20, /* 000000000010 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 17 0x11 '^Q' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x40, 0x00, /* 010000000000 */
+	0x60, 0x00, /* 011000000000 */
+	0x70, 0x00, /* 011100000000 */
+	0x78, 0x00, /* 011110000000 */
+	0x7c, 0x00, /* 011111000000 */
+	0x7e, 0x00, /* 011111100000 */
+	0x7f, 0x00, /* 011111110000 */
+	0x7f, 0x80, /* 011111111000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x7f, 0x80, /* 011111111000 */
+	0x7f, 0x00, /* 011111110000 */
+	0x7e, 0x00, /* 011111100000 */
+	0x7c, 0x00, /* 011111000000 */
+	0x78, 0x00, /* 011110000000 */
+	0x70, 0x00, /* 011100000000 */
+	0x60, 0x00, /* 011000000000 */
+	0x40, 0x00, /* 010000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 18 0x12 '^R' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x04, 0x00, /* 000001000000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x3f, 0x80, /* 001111111000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x3f, 0x80, /* 001111111000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x04, 0x00, /* 000001000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -551,24 +533,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 22 0x16 '^V' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -576,24 +557,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 23 0x17 '^W' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x04, 0x00, /* 000001000000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x3f, 0x80, /* 001111111000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x3f, 0x80, /* 001111111000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x04, 0x00, /* 000001000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -601,49 +581,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 24 0x18 '^X' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x04, 0x00, /* 000001000000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x3f, 0x80, /* 001111111000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 25 0x19 '^Y' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x3f, 0x80, /* 001111111000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x04, 0x00, /* 000001000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -651,24 +629,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 26 0x1a '^Z' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x08, 0x00, /* 000010000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x38, 0x00, /* 001110000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0xff, 0xe0, /* 111111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x38, 0x00, /* 001110000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x08, 0x00, /* 000010000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -676,24 +653,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 27 0x1b '^[' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x01, 0x00, /* 000000010000 */
+	0x01, 0x80, /* 000000011000 */
+	0x01, 0xc0, /* 000000011100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xf0, /* 011111111111 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x01, 0xc0, /* 000000011100 */
+	0x01, 0x80, /* 000000011000 */
+	0x01, 0x00, /* 000000010000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -701,24 +677,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 28 0x1c '^\' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x3f, 0xe0, /* 001111111110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -726,24 +701,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 29 0x1d '^]' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x09, 0x00, /* 000010010000 */
+	0x19, 0x80, /* 000110011000 */
+	0x39, 0xc0, /* 001110011100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0xff, 0xf0, /* 111111111111 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x39, 0xc0, /* 001110011100 */
+	0x19, 0x80, /* 000110011000 */
+	0x09, 0x00, /* 000010010000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -751,24 +725,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 30 0x1e '^^' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x04, 0x00, /* 000001000000 */
+	0x04, 0x00, /* 000001000000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x3f, 0x80, /* 001111111000 */
+	0x3f, 0x80, /* 001111111000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -776,24 +749,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 31 0x1f '^_' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x3f, 0x80, /* 001111111000 */
+	0x3f, 0x80, /* 001111111000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x04, 0x00, /* 000001000000 */
+	0x04, 0x00, /* 000001000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -3081,29 +3053,28 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 127 0x7f '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0xff, 0xf0, /* 111111111111 */
+	0xff, 0xf0, /* 111111111111 */
+	0x00, 0x00, /* 000000000000 */
 
 	/* 128 0x80 '.' */
 	0x00, 0x00, /* 000000000000 */
@@ -3826,53 +3797,51 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 158 0x9e '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
+	0x7f, 0x80, /* 011111111000 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0x60, /* 001100000110 */
+	0x30, 0x60, /* 001100000110 */
+	0x30, 0x60, /* 001100000110 */
+	0x30, 0xc0, /* 001100001100 */
+	0x37, 0x80, /* 001101111000 */
+	0x30, 0x00, /* 001100000000 */
+	0x33, 0x00, /* 001100110000 */
+	0x37, 0x80, /* 001101111000 */
+	0x33, 0x00, /* 001100110000 */
+	0x33, 0x00, /* 001100110000 */
+	0x33, 0x30, /* 001100110011 */
+	0x31, 0xe0, /* 001100011110 */
+	0x78, 0xc0, /* 011110001100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 159 0x9f '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x00, 0xc0, /* 000000001100 */
+	0x01, 0xe0, /* 000000011110 */
+	0x03, 0x30, /* 000000110011 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x7f, 0xc0, /* 011111111100 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0xcc, 0x00, /* 110011000000 */
+	0x78, 0x00, /* 011110000000 */
+	0x30, 0x00, /* 001100000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 160 0xa0 '.' */
@@ -4092,24 +4061,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 169 0xa9 '.' */
-	/* FIXME */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5413,24 +5381,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 224 0xe0 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x0f, 0x60, /* 000011110110 */
+	0x13, 0xe0, /* 000100111110 */
+	0x21, 0xc0, /* 001000011100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x70, 0x80, /* 011100001000 */
+	0x39, 0xc0, /* 001110011100 */
+	0x1f, 0x60, /* 000111110110 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5462,49 +5429,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 226 0xe2 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x3f, 0xe0, /* 001111111110 */
+	0x30, 0x60, /* 001100000110 */
+	0x30, 0x60, /* 001100000110 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 227 0xe3 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5512,49 +5477,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 228 0xe4 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x60, 0x60, /* 011000000110 */
+	0x30, 0x60, /* 001100000110 */
+	0x30, 0x00, /* 001100000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x60, /* 001100000110 */
+	0x60, 0x60, /* 011000000110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 229 0xe5 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x07, 0xe0, /* 000001111110 */
+	0x0f, 0xe0, /* 000011111110 */
+	0x13, 0x80, /* 000100111000 */
+	0x21, 0xc0, /* 001000011100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x60, 0xc0, /* 011000001100 */
+	0x70, 0x80, /* 011100001000 */
+	0x39, 0x00, /* 001110010000 */
+	0x1e, 0x00, /* 000111100000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5586,74 +5549,71 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 231 0xe7 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
+	0x19, 0x80, /* 000110011000 */
+	0x3f, 0xc0, /* 001111111100 */
+	0x66, 0x60, /* 011001100110 */
+	0x66, 0x60, /* 011001100110 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 232 0xe8 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x19, 0x80, /* 000110011000 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x19, 0x80, /* 000110011000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 233 0xe9 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x0f, 0x00, /* 000011110000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x30, 0xc0, /* 001100001100 */
+	0x60, 0x60, /* 011000000110 */
+	0x60, 0x60, /* 011000000110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x60, 0x60, /* 011000000110 */
+	0x60, 0x60, /* 011000000110 */
+	0x30, 0xc0, /* 001100001100 */
+	0x1f, 0x80, /* 000111111000 */
+	0x0f, 0x00, /* 000011110000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5661,24 +5621,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 234 0xea '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x1f, 0x00, /* 000111110000 */
+	0x31, 0x80, /* 001100011000 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x60, 0x60, /* 011000000110 */
+	0x60, 0x60, /* 011000000110 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x19, 0x80, /* 000110011000 */
+	0x19, 0x80, /* 000110011000 */
+	0xd9, 0xb0, /* 110110011011 */
+	0x79, 0xe0, /* 011110011110 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5686,49 +5645,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 235 0xeb '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
+	0x07, 0x80, /* 000001111000 */
+	0x0c, 0xc0, /* 000011001100 */
+	0x18, 0x60, /* 000110000110 */
+	0x18, 0x00, /* 000110000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x06, 0x00, /* 000001100000 */
+	0x03, 0x00, /* 000000110000 */
+	0x0f, 0x80, /* 000011111000 */
+	0x11, 0xc0, /* 000100011100 */
+	0x20, 0xe0, /* 001000001110 */
+	0x60, 0x60, /* 011000000110 */
+	0x60, 0x60, /* 011000000110 */
+	0x70, 0x40, /* 011100000100 */
+	0x38, 0x80, /* 001110001000 */
+	0x1f, 0x00, /* 000111110000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 236 0xec '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x39, 0xc0, /* 001110011100 */
+	0x6f, 0x60, /* 011011110110 */
+	0x66, 0x60, /* 011001100110 */
+	0xc6, 0x30, /* 110001100011 */
+	0xc6, 0x30, /* 110001100011 */
+	0x66, 0x60, /* 011001100110 */
+	0x6f, 0x60, /* 011011110110 */
+	0x39, 0xc0, /* 001110011100 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5736,74 +5693,71 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 237 0xed '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x00, 0xc0, /* 000000001100 */
+	0x00, 0xc0, /* 000000001100 */
+	0x01, 0x80, /* 000000011000 */
+	0x01, 0x80, /* 000000011000 */
+	0x3b, 0xc0, /* 001110111100 */
+	0x6f, 0x60, /* 011011110110 */
+	0x66, 0x60, /* 011001100110 */
+	0xc6, 0x30, /* 110001100011 */
+	0xc6, 0x30, /* 110001100011 */
+	0x66, 0x60, /* 011001100110 */
+	0x6f, 0x60, /* 011011110110 */
+	0x3d, 0xc0, /* 001111011100 */
+	0x18, 0x00, /* 000110000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x30, 0x00, /* 001100000000 */
+	0x30, 0x00, /* 001100000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 238 0xee '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
+	0x01, 0xc0, /* 000000011100 */
+	0x03, 0x00, /* 000000110000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x1f, 0xc0, /* 000111111100 */
+	0x18, 0x00, /* 000110000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x03, 0x00, /* 000000110000 */
+	0x01, 0xc0, /* 000000011100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 239 0xef '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x0f, 0x00, /* 000011110000 */
+	0x1f, 0x80, /* 000111111000 */
+	0x39, 0xc0, /* 001110011100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
+	0x30, 0xc0, /* 001100001100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5811,24 +5765,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 240 0xf0 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5860,24 +5813,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 242 0xf2 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x60, 0x00, /* 011000000000 */
+	0x38, 0x00, /* 001110000000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x03, 0x80, /* 000000111000 */
+	0x00, 0xe0, /* 000000001110 */
+	0x00, 0xe0, /* 000000001110 */
+	0x03, 0x80, /* 000000111000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x38, 0x00, /* 001110000000 */
+	0x60, 0x00, /* 011000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5885,24 +5837,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 243 0xf3 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x00, 0x60, /* 000000000110 */
+	0x01, 0xc0, /* 000000011100 */
+	0x07, 0x00, /* 000001110000 */
+	0x1c, 0x00, /* 000111000000 */
+	0x70, 0x00, /* 011100000000 */
+	0x70, 0x00, /* 011100000000 */
+	0x1c, 0x00, /* 000111000000 */
+	0x07, 0x00, /* 000001110000 */
+	0x01, 0xc0, /* 000000011100 */
+	0x00, 0x60, /* 000000000110 */
 	0x00, 0x00, /* 000000000000 */
+	0x7f, 0xe0, /* 011111111110 */
+	0x7f, 0xe0, /* 011111111110 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -5910,54 +5861,52 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 244 0xf4 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x03, 0x80, /* 000000111000 */
+	0x07, 0xc0, /* 000001111100 */
+	0x0c, 0x60, /* 000011000110 */
+	0x0c, 0x60, /* 000011000110 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
+	0x0c, 0x00, /* 000011000000 */
 
 	/* 245 0xf5 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x1c, 0x00, /* 000111000000 */
+	0x3e, 0x00, /* 001111100000 */
+	0x63, 0x00, /* 011000110000 */
+	0x63, 0x00, /* 011000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
+	0x03, 0x00, /* 000000110000 */
 
 	/* 246 0xf6 '.' */
 	0x00, 0x00, /* 000000000000 */
@@ -5984,24 +5933,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 247 0xf7 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x38, 0x00, /* 001110000000 */
+	0x6c, 0x00, /* 011011000000 */
+	0x06, 0x30, /* 000001100011 */
+	0x03, 0x60, /* 000000110110 */
+	0x39, 0xc0, /* 001110011100 */
+	0x6c, 0x00, /* 011011000000 */
+	0x06, 0x30, /* 000001100011 */
+	0x03, 0x60, /* 000000110110 */
+	0x01, 0xc0, /* 000000011100 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -6033,24 +5981,23 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 249 0xf9 '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x1c, 0x00, /* 000111000000 */
+	0x3e, 0x00, /* 001111100000 */
+	0x3e, 0x00, /* 001111100000 */
+	0x3e, 0x00, /* 001111100000 */
+	0x1c, 0x00, /* 000111000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -6067,13 +6014,13 @@
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x06, 0x00, /* 000001100000 */
-	0x0f, 0x00, /* 000011110000 */
-	0x0f, 0x00, /* 000011110000 */
-	0x06, 0x00, /* 000001100000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
+	0x18, 0x00, /* 000110000000 */
+	0x3c, 0x00, /* 001111000000 */
+	0x3c, 0x00, /* 001111000000 */
+	0x18, 0x00, /* 000110000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
@@ -6082,49 +6029,47 @@
 	0x00, 0x00, /* 000000000000 */
 
 	/* 251 0xfb '.' */
-	/* FIXME */
 	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
-	0x00, 0x00, /* 000000000000 */
+	0x07, 0xe0, /* 000001111110 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x06, 0x00, /* 000001100000 */
+	0xc6, 0x00, /* 110001100000 */
+	0x66, 0x00, /* 011001100000 */
+	0x36, 0x00, /* 001101100000 */
+	0x1e, 0x00, /* 000111100000 */
+	0x0e, 0x00, /* 000011100000 */
+	0x06, 0x00, /* 000001100000 */
+	0x02, 0x00, /* 000000100000 */
 	0x00, 0x00, /* 000000000000 */
 
 	/* 252 0xfc '.' */
-	/* FIXME */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x13, 0x80, /* 000100111000 */
+	0x3d, 0xc0, /* 001111011100 */
+	0x18, 0xc0, /* 000110001100 */
+	0x18, 0xc0, /* 000110001100 */
+	0x18, 0xc0, /* 000110001100 */
+	0x18, 0xc0, /* 000110001100 */
+	0x3d, 0xe0, /* 001111011110 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
-	0x3f, 0xc0, /* 001111111100 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
+	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
 	0x00, 0x00, /* 000000000000 */
diff --git a/drivers/video/console/fonts.c b/drivers/video/console/fonts.c
index 465d678..e79b297 100644
--- a/drivers/video/console/fonts.c
+++ b/drivers/video/console/fonts.c
@@ -36,6 +36,10 @@
 #undef NO_FONTS
     &font_vga_6x11,
 #endif
+#ifdef CONFIG_FONT_7x14
+#undef NO_FONTS
+    &font_7x14,
+#endif
 #ifdef CONFIG_FONT_SUN8x16
 #undef NO_FONTS
     &font_sun_8x16,
@@ -44,6 +48,10 @@
 #undef NO_FONTS
     &font_sun_12x22,
 #endif
+#ifdef CONFIG_FONT_10x18
+#undef NO_FONTS
+    &font_10x18,
+#endif
 #ifdef CONFIG_FONT_ACORN_8x8
 #undef NO_FONTS
     &font_acorn_8x8,
diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
index bcf59b2..d27fa91 100644
--- a/drivers/video/console/vgacon.c
+++ b/drivers/video/console/vgacon.c
@@ -95,6 +95,7 @@
 /* Description of the hardware situation */
 static unsigned long	vga_vram_base;		/* Base of video memory */
 static unsigned long	vga_vram_end;		/* End of video memory */
+static int		vga_vram_size;		/* Size of video memory */
 static u16		vga_video_port_reg;	/* Video register select port */
 static u16		vga_video_port_val;	/* Video register value port */
 static unsigned int	vga_video_num_columns;	/* Number of text columns */
@@ -288,6 +289,7 @@
 
 	vga_vram_base = VGA_MAP_MEM(vga_vram_base);
 	vga_vram_end = VGA_MAP_MEM(vga_vram_end);
+	vga_vram_size = vga_vram_end - vga_vram_base;
 
 	/*
 	 *      Find out if there is a graphics card present.
@@ -504,9 +506,13 @@
 	 */
 	vga_video_num_columns = c->vc_cols;
 	vga_video_num_lines = c->vc_rows;
+
+	/* We can only copy out the size of the video buffer here,
+	 * otherwise we get into VGA BIOS */
+
 	if (!vga_is_gfx)
 		scr_memcpyw((u16 *) c->vc_origin, (u16 *) c->vc_screenbuf,
-			    c->vc_screenbuf_size);
+			    c->vc_screenbuf_size > vga_vram_size ? vga_vram_size : c->vc_screenbuf_size);
 	return 0;		/* Redrawing not needed */
 }
 
@@ -961,7 +967,6 @@
 	if (!lines)		/* Turn scrollback off */
 		c->vc_visible_origin = c->vc_origin;
 	else {
-		int vram_size = vga_vram_end - vga_vram_base;
 		int margin = c->vc_size_row * 4;
 		int ul, we, p, st;
 
@@ -971,7 +976,7 @@
 			we = vga_rolled_over + c->vc_size_row;
 		} else {
 			ul = 0;
-			we = vram_size;
+			we = vga_vram_size;
 		}
 		p = (c->vc_visible_origin - vga_vram_base - ul + we) % we +
 		    lines * c->vc_size_row;
@@ -1012,9 +1017,13 @@
 		c->vc_x = ORIG_X;
 		c->vc_y = ORIG_Y;
 	}
+
+	/* We can't copy in more then the size of the video buffer,
+	 * or we'll be copying in VGA BIOS */
+
 	if (!vga_is_gfx)
 		scr_memcpyw((u16 *) c->vc_screenbuf, (u16 *) c->vc_origin,
-			    c->vc_screenbuf_size);
+			    c->vc_screenbuf_size > vga_vram_size ? vga_vram_size : c->vc_screenbuf_size);
 }
 
 static int vgacon_scroll(struct vc_data *c, int t, int b, int dir,
diff --git a/drivers/video/fbmem.c b/drivers/video/fbmem.c
index 8cef020..2222de6 100644
--- a/drivers/video/fbmem.c
+++ b/drivers/video/fbmem.c
@@ -76,70 +76,22 @@
 EXPORT_SYMBOL(fb_get_color_depth);
 
 /*
- * Drawing helpers.
+ * Data padding functions.
  */
-void fb_iomove_buf_aligned(struct fb_info *info, struct fb_pixmap *buf,
-			   u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch,
-			   u32 height)
+void fb_pad_aligned_buffer(u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch, u32 height)
 {
 	int i;
 
 	for (i = height; i--; ) {
-		buf->outbuf(info, dst, src, s_pitch);
+		memcpy(dst, src, s_pitch);
 		src += s_pitch;
 		dst += d_pitch;
 	}
 }
+EXPORT_SYMBOL(fb_pad_aligned_buffer);
 
-void fb_sysmove_buf_aligned(struct fb_info *info, struct fb_pixmap *buf,
-			    u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch,
-			    u32 height)
-{
-	int i, j;
-
-	for (i = height; i--; ) {
-		for (j = 0; j < s_pitch; j++)
-			dst[j] = src[j];
-		src += s_pitch;
-		dst += d_pitch;
-	}
-}
-
-void fb_iomove_buf_unaligned(struct fb_info *info, struct fb_pixmap *buf,
-			     u8 *dst, u32 d_pitch, u8 *src, u32 idx,
-			     u32 height, u32 shift_high, u32 shift_low,
-			     u32 mod)
-{
-	u8 mask = (u8) (0xfff << shift_high), tmp;
-	int i, j;
-
-	for (i = height; i--; ) {
-		for (j = 0; j < idx; j++) {
-			tmp = buf->inbuf(info, dst+j);
-			tmp &= mask;
-			tmp |= *src >> shift_low;
-			buf->outbuf(info, dst+j, &tmp, 1);
-			tmp = *src << shift_high;
-			buf->outbuf(info, dst+j+1, &tmp, 1);
-			src++;
-		}
-		tmp = buf->inbuf(info, dst+idx);
-		tmp &= mask;
-		tmp |= *src >> shift_low;
-		buf->outbuf(info, dst+idx, &tmp, 1);
-		if (shift_high < mod) {
-			tmp = *src << shift_high;
-			buf->outbuf(info, dst+idx+1, &tmp, 1);
-		}	
-		src++;
-		dst += d_pitch;
-	}
-}
-
-void fb_sysmove_buf_unaligned(struct fb_info *info, struct fb_pixmap *buf,
-			      u8 *dst, u32 d_pitch, u8 *src, u32 idx,
-			      u32 height, u32 shift_high, u32 shift_low,
-			      u32 mod)
+void fb_pad_unaligned_buffer(u8 *dst, u32 d_pitch, u8 *src, u32 idx, u32 height,
+				u32 shift_high, u32 shift_low, u32 mod)
 {
 	u8 mask = (u8) (0xfff << shift_high), tmp;
 	int i, j;
@@ -166,6 +118,7 @@
 		dst += d_pitch;
 	}
 }
+EXPORT_SYMBOL(fb_pad_unaligned_buffer);
 
 /*
  * we need to lock this section since fb_cursor
@@ -1081,7 +1034,7 @@
 			fb_info->pixmap.size = FBPIXMAPSIZE;
 			fb_info->pixmap.buf_align = 1;
 			fb_info->pixmap.scan_align = 1;
-			fb_info->pixmap.access_align = 4;
+			fb_info->pixmap.access_align = 32;
 			fb_info->pixmap.flags = FB_PIXMAP_DEFAULT;
 		}
 	}	
@@ -1357,10 +1310,6 @@
 EXPORT_SYMBOL(fb_blank);
 EXPORT_SYMBOL(fb_pan_display);
 EXPORT_SYMBOL(fb_get_buffer_offset);
-EXPORT_SYMBOL(fb_iomove_buf_unaligned);
-EXPORT_SYMBOL(fb_iomove_buf_aligned);
-EXPORT_SYMBOL(fb_sysmove_buf_unaligned);
-EXPORT_SYMBOL(fb_sysmove_buf_aligned);
 EXPORT_SYMBOL(fb_set_suspend);
 EXPORT_SYMBOL(fb_register_client);
 EXPORT_SYMBOL(fb_unregister_client);
diff --git a/drivers/video/i810/i810_main.c b/drivers/video/i810/i810_main.c
index a9a618f..7513fb9 100644
--- a/drivers/video/i810/i810_main.c
+++ b/drivers/video/i810/i810_main.c
@@ -1885,6 +1885,7 @@
 	memset(info->pixmap.addr, 0, 8*1024);
 	info->pixmap.size = 8*1024;
 	info->pixmap.buf_align = 8;
+	info->pixmap.access_align = 32;
 	info->pixmap.flags = FB_PIXMAP_SYSTEM;
 
 	if ((err = i810_allocate_pci_resource(par, entry))) {
diff --git a/drivers/video/intelfb/intelfbdrv.c b/drivers/video/intelfb/intelfbdrv.c
index 25f9a9a..298bc9c 100644
--- a/drivers/video/intelfb/intelfbdrv.c
+++ b/drivers/video/intelfb/intelfbdrv.c
@@ -214,7 +214,7 @@
 
 /* PCI driver module table */
 static struct pci_driver intelfb_driver = {
-	.name =		"Intel(R) " SUPPORTED_CHIPSETS " Framebuffer Driver",
+	.name =		"intelfb",
 	.id_table =	intelfb_pci_table,
 	.probe =	intelfb_pci_register,
 	.remove =	__devexit_p(intelfb_pci_unregister)
@@ -238,12 +238,15 @@
 static int probeonly    = 0;
 static int idonly       = 0;
 static int bailearly    = 0;
+static int voffset	= 48;
 static char *mode       = NULL;
 
 module_param(accel, bool, S_IRUGO);
 MODULE_PARM_DESC(accel, "Enable console acceleration");
 module_param(vram, int, S_IRUGO);
 MODULE_PARM_DESC(vram, "System RAM to allocate to framebuffer in MiB");
+module_param(voffset, int, S_IRUGO);
+MODULE_PARM_DESC(voffset, "Offset of framebuffer in MiB");
 module_param(hwcursor, bool, S_IRUGO);
 MODULE_PARM_DESC(hwcursor, "Enable HW cursor");
 module_param(mtrr, bool, S_IRUGO);
@@ -503,6 +506,7 @@
 	struct agp_bridge_data *bridge;
  	int aperture_bar = 0;
  	int mmio_bar = 1;
+	int offset;
 
 	DBG_MSG("intelfb_pci_register\n");
 
@@ -659,17 +663,21 @@
 		return -ENODEV;
 	}
 
+	if (MB(voffset) < stolen_size)
+		offset = (stolen_size >> 12);
+	else
+		offset = ROUND_UP_TO_PAGE(MB(voffset))/GTT_PAGE_SIZE;
+
 	/* set the mem offsets - set them after the already used pages */
 	if (dinfo->accel) {
-		dinfo->ring.offset = (stolen_size >> 12)
-			+ gtt_info.current_memory;
+		dinfo->ring.offset = offset + gtt_info.current_memory;
 	}
 	if (dinfo->hwcursor) {
-		dinfo->cursor.offset = (stolen_size >> 12) +
+		dinfo->cursor.offset = offset +
 			+ gtt_info.current_memory + (dinfo->ring.size >> 12);
 	}
 	if (dinfo->fbmem_gart) {
-		dinfo->fb.offset = (stolen_size >> 12) +
+		dinfo->fb.offset = offset +
 			+ gtt_info.current_memory + (dinfo->ring.size >> 12)
 			+ (dinfo->cursor.size >> 12);
 	}
@@ -1083,6 +1091,7 @@
 
 	info->pixmap.size = 64*1024;
 	info->pixmap.buf_align = 8;
+	info->pixmap.access_align = 32;
 	info->pixmap.flags = FB_PIXMAP_SYSTEM;
 
 	if (intelfb_init_var(dinfo))
@@ -1293,7 +1302,7 @@
 
 	intelfb_blank(FB_BLANK_POWERDOWN, info);
 
-	if (dinfo->accel)
+	if (ACCEL(dinfo, info))
 		intelfbhw_2d_stop(dinfo);
 
  	memcpy(hw, &dinfo->save_state, sizeof(*hw));
@@ -1309,7 +1318,7 @@
 
 	update_dinfo(dinfo, &info->var);
 
-	if (dinfo->accel)
+	if (ACCEL(dinfo, info))
 		intelfbhw_2d_start(dinfo);
 
 	intelfb_pan_display(&info->var, info);
diff --git a/drivers/video/nvidia/nvidia.c b/drivers/video/nvidia/nvidia.c
index 47733f5..b2e6b24 100644
--- a/drivers/video/nvidia/nvidia.c
+++ b/drivers/video/nvidia/nvidia.c
@@ -516,9 +516,9 @@
 static void nvidiafb_load_cursor_image(struct nvidia_par *par, u8 * data8,
 				       u16 bg, u16 fg, u32 w, u32 h)
 {
+	u32 *data = (u32 *) data8;
 	int i, j, k = 0;
 	u32 b, tmp;
-	u32 *data = (u32 *) data8;
 
 	w = (w + 1) & ~1;
 
@@ -890,11 +890,11 @@
 {
 	struct nvidia_par *par = info->par;
 	u8 data[MAX_CURS * MAX_CURS / 8];
-	u16 fg, bg;
 	int i, set = cursor->set;
+	u16 fg, bg;
 
 	if (cursor->image.width > MAX_CURS || cursor->image.height > MAX_CURS)
-		return soft_cursor(info, cursor);
+		return -ENXIO;
 
 	NVShowHideCursor(par, 0);
 
@@ -931,21 +931,18 @@
 		if (src) {
 			switch (cursor->rop) {
 			case ROP_XOR:
-				for (i = 0; i < s_pitch * cursor->image.height;
-				     i++)
+				for (i = 0; i < s_pitch * cursor->image.height; i++)
 					src[i] = dat[i] ^ msk[i];
 				break;
 			case ROP_COPY:
 			default:
-				for (i = 0; i < s_pitch * cursor->image.height;
-				     i++)
+				for (i = 0; i < s_pitch * cursor->image.height; i++)
 					src[i] = dat[i] & msk[i];
 				break;
 			}
 
-			fb_sysmove_buf_aligned(info, &info->pixmap, data,
-					       d_pitch, src, s_pitch,
-					       cursor->image.height);
+			fb_pad_aligned_buffer(data, d_pitch, src, s_pitch,
+						cursor->image.height);
 
 			bg = ((info->cmap.red[bg_idx] & 0xf8) << 7) |
 			    ((info->cmap.green[bg_idx] & 0xf8) << 2) |
@@ -1348,6 +1345,7 @@
 
 	info->pixmap.scan_align = 4;
 	info->pixmap.buf_align = 4;
+	info->pixmap.access_align = 32;
 	info->pixmap.size = 8 * 1024;
 	info->pixmap.flags = FB_PIXMAP_SYSTEM;
 
diff --git a/drivers/video/pm3fb.c b/drivers/video/pm3fb.c
index 8e024aa..e0dad94 100644
--- a/drivers/video/pm3fb.c
+++ b/drivers/video/pm3fb.c
@@ -5,7 +5,7 @@
  *  Based on code written by:
  *           Sven Luther, <luther@dpt-info.u-strasbg.fr>
  *           Alan Hourihane, <alanh@fairlite.demon.co.uk>
- *           Russel King, <rmk@arm.linux.org.uk>
+ *           Russell King, <rmk@arm.linux.org.uk>
  *  Based on linux/drivers/video/skeletonfb.c:
  *	Copyright (C) 1997 Geert Uytterhoeven
  *  Based on linux/driver/video/pm2fb.c:
diff --git a/drivers/video/riva/fbdev.c b/drivers/video/riva/fbdev.c
index b0c886d..6a9e183 100644
--- a/drivers/video/riva/fbdev.c
+++ b/drivers/video/riva/fbdev.c
@@ -1582,12 +1582,11 @@
 {
 	struct riva_par *par = (struct riva_par *) info->par;
 	u8 data[MAX_CURS * MAX_CURS/8];
-	u16 fg, bg;
 	int i, set = cursor->set;
+	u16 fg, bg;
 
-	if (cursor->image.width > MAX_CURS ||
-	    cursor->image.height > MAX_CURS)
-		return soft_cursor(info, cursor);
+	if (cursor->image.width > MAX_CURS || cursor->image.height > MAX_CURS)
+		return -ENXIO;
 
 	par->riva.ShowHideCursor(&par->riva, 0);
 
@@ -1625,21 +1624,18 @@
 		if (src) {
 			switch (cursor->rop) {
 			case ROP_XOR:
-				for (i = 0; i < s_pitch * cursor->image.height;
-				     i++)
+				for (i = 0; i < s_pitch * cursor->image.height; i++)
 					src[i] = dat[i] ^ msk[i];
 				break;
 			case ROP_COPY:
 			default:
-				for (i = 0; i < s_pitch * cursor->image.height;
-				     i++)
+				for (i = 0; i < s_pitch * cursor->image.height; i++)
 					src[i] = dat[i] & msk[i];
 				break;
 			}
 
-			fb_sysmove_buf_aligned(info, &info->pixmap, data,
-					       d_pitch, src, s_pitch,
-					       cursor->image.height);
+			fb_pad_aligned_buffer(data, d_pitch, src, s_pitch,
+						cursor->image.height);
 
 			bg = ((info->cmap.red[bg_idx] & 0xf8) << 7) |
 				((info->cmap.green[bg_idx] & 0xf8) << 2) |
@@ -1727,6 +1723,7 @@
 
 	info->pixmap.size = 8 * 1024;
 	info->pixmap.buf_align = 4;
+	info->pixmap.access_align = 32;
 	info->pixmap.flags = FB_PIXMAP_SYSTEM;
 	info->var.yres_virtual = -1;
 	NVTRACE_LEAVE();
diff --git a/drivers/video/s1d13xxxfb.c b/drivers/video/s1d13xxxfb.c
index b637c38..789de13 100644
--- a/drivers/video/s1d13xxxfb.c
+++ b/drivers/video/s1d13xxxfb.c
@@ -493,7 +493,7 @@
 }
 
 
-static int __devexit
+static int
 s1d13xxxfb_remove(struct device *dev)
 {
 	struct fb_info *info = dev_get_drvdata(dev);
diff --git a/drivers/video/savage/savagefb_driver.c b/drivers/video/savage/savagefb_driver.c
index 03d74e8..8fadcda 100644
--- a/drivers/video/savage/savagefb_driver.c
+++ b/drivers/video/savage/savagefb_driver.c
@@ -1897,7 +1897,7 @@
 		info->pixmap.size = 8*1024;
 		info->pixmap.scan_align = 4;
 		info->pixmap.buf_align = 4;
-		info->pixmap.access_align = 4;
+		info->pixmap.access_align = 32;
 
 		fb_alloc_cmap (&info->cmap, NR_PALETTE, 0);
 		info->flags |= FBINFO_HWACCEL_COPYAREA |
diff --git a/drivers/video/softcursor.c b/drivers/video/softcursor.c
index 13a4511..229c4bc 100644
--- a/drivers/video/softcursor.c
+++ b/drivers/video/softcursor.c
@@ -58,17 +58,10 @@
 	} else 
 		memcpy(src, image->data, dsize);
 	
-	if (info->pixmap.outbuf)
-		fb_iomove_buf_aligned(info, &info->pixmap, dst, d_pitch, src,
-				  s_pitch, image->height);
-	else
-		fb_sysmove_buf_aligned(info, &info->pixmap, dst, d_pitch, src,
-				   s_pitch, image->height);
-
+	fb_pad_aligned_buffer(dst, d_pitch, src, s_pitch, image->height);
 	image->data = dst;
 	info->fbops->fb_imageblit(info, image);
 	kfree(src);
-
 	return 0;
 }
 
diff --git a/drivers/video/vesafb.c b/drivers/video/vesafb.c
index 3027841..f3069b0 100644
--- a/drivers/video/vesafb.c
+++ b/drivers/video/vesafb.c
@@ -271,7 +271,7 @@
 
 	if (!request_mem_region(vesafb_fix.smem_start, size_total, "vesafb")) {
 		printk(KERN_WARNING
-		       "vesafb: abort, cannot reserve video memory at 0x%lx\n",
+		       "vesafb: cannot reserve video memory at 0x%lx\n",
 			vesafb_fix.smem_start);
 		/* We cannot make this fatal. Sometimes this comes from magic
 		   spaces our resource handlers simply don't know about */
@@ -279,13 +279,13 @@
 
 	info = framebuffer_alloc(sizeof(u32) * 256, &dev->dev);
 	if (!info) {
-		release_mem_region(vesafb_fix.smem_start, vesafb_fix.smem_len);
+		release_mem_region(vesafb_fix.smem_start, size_total);
 		return -ENOMEM;
 	}
 	info->pseudo_palette = info->par;
 	info->par = NULL;
 
-        info->screen_base = ioremap(vesafb_fix.smem_start, vesafb_fix.smem_len);
+	info->screen_base = ioremap(vesafb_fix.smem_start, vesafb_fix.smem_len);
 	if (!info->screen_base) {
 		printk(KERN_ERR
 		       "vesafb: abort, cannot ioremap video memory 0x%x @ 0x%lx\n",
@@ -386,7 +386,7 @@
 	request_region(0x3c0, 32, "vesafb");
 
 	if (mtrr) {
-		int temp_size = size_total;
+		unsigned int temp_size = size_total;
 		/* Find the largest power-of-two */
 		while (temp_size & (temp_size - 1))
                 	temp_size &= (temp_size - 1);
diff --git a/fs/Kconfig b/fs/Kconfig
index 6a4ad4b..178e274 100644
--- a/fs/Kconfig
+++ b/fs/Kconfig
@@ -741,56 +741,6 @@
 
 	Designers of embedded systems may wish to say N here to conserve space.
 
-config DEVFS_FS
-	bool "/dev file system support (OBSOLETE)"
-	depends on EXPERIMENTAL
-	help
-	  This is support for devfs, a virtual file system (like /proc) which
-	  provides the file system interface to device drivers, normally found
-	  in /dev. Devfs does not depend on major and minor number
-	  allocations. Device drivers register entries in /dev which then
-	  appear automatically, which means that the system administrator does
-	  not have to create character and block special device files in the
-	  /dev directory using the mknod command (or MAKEDEV script) anymore.
-
-	  This is work in progress. If you want to use this, you *must* read
-	  the material in <file:Documentation/filesystems/devfs/>, especially
-	  the file README there.
-
-	  Note that devfs no longer manages /dev/pts!  If you are using UNIX98
-	  ptys, you will also need to mount the /dev/pts filesystem (devpts).
-
-	  Note that devfs has been obsoleted by udev,
-	  <http://www.kernel.org/pub/linux/utils/kernel/hotplug/>.
-	  It has been stripped down to a bare minimum and is only provided for
-	  legacy installations that use its naming scheme which is
-	  unfortunately different from the names normal Linux installations
-	  use.
-
-	  If unsure, say N.
-
-config DEVFS_MOUNT
-	bool "Automatically mount at boot"
-	depends on DEVFS_FS
-	help
-	  This option appears if you have CONFIG_DEVFS_FS enabled. Setting
-	  this to 'Y' will make the kernel automatically mount devfs onto /dev
-	  when the system is booted, before the init thread is started.
-	  You can override this with the "devfs=nomount" boot option.
-
-	  If unsure, say N.
-
-config DEVFS_DEBUG
-	bool "Debug devfs"
-	depends on DEVFS_FS
-	help
-	  If you say Y here, then the /dev file system code will generate
-	  debugging messages. See the file
-	  <file:Documentation/filesystems/devfs/boot-options> for more
-	  details.
-
-	  If unsure, say N.
-
 config DEVPTS_FS_XATTR
 	bool "/dev/pts Extended Attributes"
 	depends on UNIX98_PTYS
diff --git a/fs/autofs4/autofs_i.h b/fs/autofs4/autofs_i.h
index c7b2b88..9c09641 100644
--- a/fs/autofs4/autofs_i.h
+++ b/fs/autofs4/autofs_i.h
@@ -185,6 +185,19 @@
 int autofs4_wait_release(struct autofs_sb_info *,autofs_wqt_t,int);
 void autofs4_catatonic_mode(struct autofs_sb_info *);
 
+static inline int autofs4_follow_mount(struct vfsmount **mnt, struct dentry **dentry)
+{
+	int res = 0;
+
+	while (d_mountpoint(*dentry)) {
+		int followed = follow_down(mnt, dentry);
+		if (!followed)
+			break;
+		res = 1;
+	}
+	return res;
+}
+
 static inline int simple_positive(struct dentry *dentry)
 {
 	return dentry->d_inode && !d_unhashed(dentry);
diff --git a/fs/autofs4/expire.c b/fs/autofs4/expire.c
index 500425e..feb6ac4 100644
--- a/fs/autofs4/expire.c
+++ b/fs/autofs4/expire.c
@@ -56,12 +56,9 @@
 	mntget(mnt);
 	dget(dentry);
 
-	if (!follow_down(&mnt, &dentry))
+	if (!autofs4_follow_mount(&mnt, &dentry))
 		goto done;
 
-	while (d_mountpoint(dentry) && follow_down(&mnt, &dentry))
-		;
-
 	/* This is an autofs submount, we can't expire it */
 	if (is_autofs4_dentry(dentry))
 		goto done;
diff --git a/fs/autofs4/root.c b/fs/autofs4/root.c
index 3765c04..2a771ec 100644
--- a/fs/autofs4/root.c
+++ b/fs/autofs4/root.c
@@ -205,7 +205,11 @@
 		struct vfsmount *fp_mnt = mntget(mnt);
 		struct dentry *fp_dentry = dget(dentry);
 
-		while (follow_down(&fp_mnt, &fp_dentry) && d_mountpoint(fp_dentry));
+		if (!autofs4_follow_mount(&fp_mnt, &fp_dentry)) {
+			dput(fp_dentry);
+			mntput(fp_mnt);
+			return -ENOENT;
+		}
 
 		fp = dentry_open(fp_dentry, fp_mnt, file->f_flags);
 		status = PTR_ERR(fp);
@@ -302,7 +306,14 @@
 		
 		DPRINTK("expire done status=%d", status);
 		
-		return 0;
+		/*
+		 * If the directory still exists the mount request must
+		 * continue otherwise it can't be followed at the right
+		 * time during the walk.
+		 */
+		status = d_invalidate(dentry);
+		if (status != -EBUSY)
+			return 0;
 	}
 
 	DPRINTK("dentry=%p %.*s ino=%p",
diff --git a/fs/autofs4/waitq.c b/fs/autofs4/waitq.c
index 5a40d36..fa2348d 100644
--- a/fs/autofs4/waitq.c
+++ b/fs/autofs4/waitq.c
@@ -191,6 +191,13 @@
 	}
 
 	if ( !wq ) {
+		/* Can't wait for an expire if there's no mount */
+		if (notify == NFY_NONE && !d_mountpoint(dentry)) {
+			kfree(name);
+			up(&sbi->wq_sem);
+			return -ENOENT;
+		}
+
 		/* Create a new wait queue */
 		wq = kmalloc(sizeof(struct autofs_wait_queue),GFP_KERNEL);
 		if ( !wq ) {
diff --git a/fs/binfmt_aout.c b/fs/binfmt_aout.c
index 009b892..dd9baab 100644
--- a/fs/binfmt_aout.c
+++ b/fs/binfmt_aout.c
@@ -316,6 +316,7 @@
 	current->mm->brk = ex.a_bss +
 		(current->mm->start_brk = N_BSSADDR(ex));
 	current->mm->free_area_cache = current->mm->mmap_base;
+	current->mm->cached_hole_size = 0;
 
 	set_mm_counter(current->mm, rss, 0);
 	current->mm->mmap = NULL;
diff --git a/fs/binfmt_elf.c b/fs/binfmt_elf.c
index f8f6b6b..7976a23 100644
--- a/fs/binfmt_elf.c
+++ b/fs/binfmt_elf.c
@@ -775,6 +775,7 @@
 	   change some of these later */
 	set_mm_counter(current->mm, rss, 0);
 	current->mm->free_area_cache = current->mm->mmap_base;
+	current->mm->cached_hole_size = 0;
 	retval = setup_arg_pages(bprm, randomize_stack_top(STACK_TOP),
 				 executable_stack);
 	if (retval < 0) {
diff --git a/fs/buffer.c b/fs/buffer.c
index 7e9e409..0befa72 100644
--- a/fs/buffer.c
+++ b/fs/buffer.c
@@ -528,7 +528,7 @@
 	for_each_pgdat(pgdat) {
 		zones = pgdat->node_zonelists[GFP_NOFS&GFP_ZONEMASK].zones;
 		if (*zones)
-			try_to_free_pages(zones, GFP_NOFS, 0);
+			try_to_free_pages(zones, GFP_NOFS);
 	}
 }
 
diff --git a/fs/hugetlbfs/inode.c b/fs/hugetlbfs/inode.c
index 2af3338..3a9b6d1 100644
--- a/fs/hugetlbfs/inode.c
+++ b/fs/hugetlbfs/inode.c
@@ -122,6 +122,9 @@
 
 	start_addr = mm->free_area_cache;
 
+	if (len <= mm->cached_hole_size)
+		start_addr = TASK_UNMAPPED_BASE;
+
 full_search:
 	addr = ALIGN(start_addr, HPAGE_SIZE);
 
diff --git a/fs/isofs/dir.c b/fs/isofs/dir.c
index 6030956..7901ac9 100644
--- a/fs/isofs/dir.c
+++ b/fs/isofs/dir.c
@@ -193,12 +193,17 @@
 
 		/* Handle everything else.  Do name translation if there
 		   is no Rock Ridge NM field. */
-		if (sbi->s_unhide == 'n') {
-			/* Do not report hidden or associated files */
-			if (de->flags[-sbi->s_high_sierra] & 5) {
-				filp->f_pos += de_len;
-				continue;
-			}
+
+		/*
+		 * Do not report hidden files if so instructed, or associated
+		 * files unless instructed to do so
+		 */
+		if ((sbi->s_hide == 'y' &&
+				(de->flags[-sbi->s_high_sierra] & 1)) ||
+		      (sbi->s_showassoc =='n' &&
+				(de->flags[-sbi->s_high_sierra] & 4))) {
+			filp->f_pos += de_len;
+			continue;
 		}
 
 		map = 1;
diff --git a/fs/isofs/inode.c b/fs/isofs/inode.c
index abd7b12..1652de1 100644
--- a/fs/isofs/inode.c
+++ b/fs/isofs/inode.c
@@ -28,11 +28,6 @@
 
 #define BEQUIET
 
-#ifdef LEAK_CHECK
-static int check_malloc;
-static int check_bread;
-#endif
-
 static int isofs_hashi(struct dentry *parent, struct qstr *qstr);
 static int isofs_hash(struct dentry *parent, struct qstr *qstr);
 static int isofs_dentry_cmpi(struct dentry *dentry, struct qstr *a, struct qstr *b);
@@ -55,11 +50,6 @@
 	}
 #endif
 
-#ifdef LEAK_CHECK
-	printk("Outstanding mallocs:%d, outstanding buffers: %d\n",
-	       check_malloc, check_bread);
-#endif
-
 	kfree(sbi);
 	sb->s_fs_info = NULL;
 	return;
@@ -73,7 +63,7 @@
 static struct inode *isofs_alloc_inode(struct super_block *sb)
 {
 	struct iso_inode_info *ei;
-	ei = (struct iso_inode_info *)kmem_cache_alloc(isofs_inode_cachep, SLAB_KERNEL);
+	ei = kmem_cache_alloc(isofs_inode_cachep, SLAB_KERNEL);
 	if (!ei)
 		return NULL;
 	return &ei->vfs_inode;
@@ -84,9 +74,9 @@
 	kmem_cache_free(isofs_inode_cachep, ISOFS_I(inode));
 }
 
-static void init_once(void * foo, kmem_cache_t * cachep, unsigned long flags)
+static void init_once(void *foo, kmem_cache_t * cachep, unsigned long flags)
 {
-	struct iso_inode_info *ei = (struct iso_inode_info *) foo;
+	struct iso_inode_info *ei = foo;
 
 	if ((flags & (SLAB_CTOR_VERIFY|SLAB_CTOR_CONSTRUCTOR)) ==
 	    SLAB_CTOR_CONSTRUCTOR)
@@ -107,7 +97,8 @@
 static void destroy_inodecache(void)
 {
 	if (kmem_cache_destroy(isofs_inode_cachep))
-		printk(KERN_INFO "iso_inode_cache: not all structures were freed\n");
+		printk(KERN_INFO "iso_inode_cache: not all structures were "
+					"freed\n");
 }
 
 static int isofs_remount(struct super_block *sb, int *flags, char *data)
@@ -144,7 +135,7 @@
 	{
 		.d_hash		= isofs_hashi_ms,
 		.d_compare	= isofs_dentry_cmpi_ms,
-	}
+	},
 #endif
 };
 
@@ -153,7 +144,8 @@
 	char rock;
 	char joliet;
 	char cruft;
-	char unhide;
+	char hide;
+	char showassoc;
 	char nocompress;
 	unsigned char check;
 	unsigned int blocksize;
@@ -219,8 +211,8 @@
 /*
  * Case insensitive compare of two isofs names.
  */
-static int
-isofs_dentry_cmpi_common(struct dentry *dentry,struct qstr *a,struct qstr *b,int ms)
+static int isofs_dentry_cmpi_common(struct dentry *dentry, struct qstr *a,
+				struct qstr *b, int ms)
 {
 	int alen, blen;
 
@@ -243,8 +235,8 @@
 /*
  * Case sensitive compare of two isofs names.
  */
-static int
-isofs_dentry_cmp_common(struct dentry *dentry,struct qstr *a,struct qstr *b,int ms)
+static int isofs_dentry_cmp_common(struct dentry *dentry, struct qstr *a,
+					struct qstr *b, int ms)
 {
 	int alen, blen;
 
@@ -318,13 +310,15 @@
 	Opt_block, Opt_check_r, Opt_check_s, Opt_cruft, Opt_gid, Opt_ignore,
 	Opt_iocharset, Opt_map_a, Opt_map_n, Opt_map_o, Opt_mode, Opt_nojoliet,
 	Opt_norock, Opt_sb, Opt_session, Opt_uid, Opt_unhide, Opt_utf8, Opt_err,
-	Opt_nocompress,
+	Opt_nocompress, Opt_hide, Opt_showassoc,
 };
 
 static match_table_t tokens = {
 	{Opt_norock, "norock"},
 	{Opt_nojoliet, "nojoliet"},
 	{Opt_unhide, "unhide"},
+	{Opt_hide, "hide"},
+	{Opt_showassoc, "showassoc"},
 	{Opt_cruft, "cruft"},
 	{Opt_utf8, "utf8"},
 	{Opt_iocharset, "iocharset=%s"},
@@ -356,7 +350,7 @@
 	{Opt_err, NULL}
 };
 
-static int parse_options(char *options, struct iso9660_options * popt)
+static int parse_options(char *options, struct iso9660_options *popt)
 {
 	char *p;
 	int option;
@@ -365,7 +359,8 @@
 	popt->rock = 'y';
 	popt->joliet = 'y';
 	popt->cruft = 'n';
-	popt->unhide = 'n';
+	popt->hide = 'n';
+	popt->showassoc = 'n';
 	popt->check = 'u';		/* unset */
 	popt->nocompress = 0;
 	popt->blocksize = 1024;
@@ -398,8 +393,12 @@
 		case Opt_nojoliet:
 			popt->joliet = 'n';
 			break;
+		case Opt_hide:
+			popt->hide = 'y';
+			break;
 		case Opt_unhide:
-			popt->unhide = 'y';
+		case Opt_showassoc:
+			popt->showassoc = 'y';
 			break;
 		case Opt_cruft:
 			popt->cruft = 'y';
@@ -493,7 +492,7 @@
  */
 #define WE_OBEY_THE_WRITTEN_STANDARDS 1
 
-static unsigned int isofs_get_last_session(struct super_block *sb,s32 session )
+static unsigned int isofs_get_last_session(struct super_block *sb, s32 session)
 {
 	struct cdrom_multisession ms_info;
 	unsigned int vol_desc_start;
@@ -518,7 +517,8 @@
 		printk(KERN_ERR "Invalid session number or type of track\n");
 	}
 	i = ioctl_by_bdev(bdev, CDROMMULTISESSION, (unsigned long) &ms_info);
-	if(session > 0) printk(KERN_ERR "Invalid session number\n");
+	if (session > 0)
+		printk(KERN_ERR "Invalid session number\n");
 #if 0
 	printk("isofs.inode: CDROMMULTISESSION: rc=%d\n",i);
 	if (i==0) {
@@ -557,13 +557,13 @@
 	struct iso9660_options		opt;
 	struct isofs_sb_info	      * sbi;
 
-	sbi = kmalloc(sizeof(struct isofs_sb_info), GFP_KERNEL);
+	sbi = kmalloc(sizeof(*sbi), GFP_KERNEL);
 	if (!sbi)
 		return -ENOMEM;
 	s->s_fs_info = sbi;
-	memset(sbi, 0, sizeof(struct isofs_sb_info));
+	memset(sbi, 0, sizeof(*sbi));
 
-	if (!parse_options((char *) data, &opt))
+	if (!parse_options((char *)data, &opt))
 		goto out_freesbi;
 
 	/*
@@ -792,7 +792,8 @@
 	sbi->s_rock = (opt.rock == 'y' ? 2 : 0);
 	sbi->s_rock_offset = -1; /* initial offset, will guess until SP is found*/
 	sbi->s_cruft = opt.cruft;
-	sbi->s_unhide = opt.unhide;
+	sbi->s_hide = opt.hide;
+	sbi->s_showassoc = opt.showassoc;
 	sbi->s_uid = opt.uid;
 	sbi->s_gid = opt.gid;
 	sbi->s_utf8 = opt.utf8;
@@ -1002,7 +1003,6 @@
 		rv++;
 	}
 
-
 abort:
 	unlock_kernel();
 	return rv;
@@ -1014,7 +1014,7 @@
 static int isofs_get_block(struct inode *inode, sector_t iblock,
 		    struct buffer_head *bh_result, int create)
 {
-	if ( create ) {
+	if (create) {
 		printk("isofs_get_block: Kernel tries to allocate a block\n");
 		return -EROFS;
 	}
@@ -1061,19 +1061,17 @@
 
 static inline void test_and_set_uid(uid_t *p, uid_t value)
 {
-	if(value) {
+	if (value)
 		*p = value;
-	}
 }
 
 static inline void test_and_set_gid(gid_t *p, gid_t value)
 {
-        if(value) {
+        if (value)
                 *p = value;
-        }
 }
 
-static int isofs_read_level3_size(struct inode * inode)
+static int isofs_read_level3_size(struct inode *inode)
 {
 	unsigned long bufsize = ISOFS_BUFFER_SIZE(inode);
 	int high_sierra = ISOFS_SB(inode->i_sb)->s_high_sierra;
@@ -1136,7 +1134,7 @@
 				bh = sb_bread(inode->i_sb, block);
 				if (!bh)
 					goto out_noread;
-				memcpy((void *) tmpde + slop, bh->b_data, offset);
+				memcpy((void *)tmpde+slop, bh->b_data, offset);
 			}
 			de = tmpde;
 		}
@@ -1150,12 +1148,11 @@
 		more_entries = de->flags[-high_sierra] & 0x80;
 
 		i++;
-		if(i > 100)
+		if (i > 100)
 			goto out_toomany;
-	} while(more_entries);
+	} while (more_entries);
 out:
-	if (tmpde)
-		kfree(tmpde);
+	kfree(tmpde);
 	if (bh)
 		brelse(bh);
 	return 0;
@@ -1179,7 +1176,7 @@
 	goto out;
 }
 
-static void isofs_read_inode(struct inode * inode)
+static void isofs_read_inode(struct inode *inode)
 {
 	struct super_block *sb = inode->i_sb;
 	struct isofs_sb_info *sbi = ISOFS_SB(sb);
@@ -1249,7 +1246,7 @@
 	ei->i_format_parm[2] = 0;
 
 	ei->i_section_size = isonum_733 (de->size);
-	if(de->flags[-high_sierra] & 0x80) {
+	if (de->flags[-high_sierra] & 0x80) {
 		if(isofs_read_level3_size(inode)) goto fail;
 	} else {
 		ei->i_next_section_block = 0;
@@ -1336,16 +1333,16 @@
 		/* XXX - parse_rock_ridge_inode() had already set i_rdev. */
 		init_special_inode(inode, inode->i_mode, inode->i_rdev);
 
- out:
+out:
 	if (tmpde)
 		kfree(tmpde);
 	if (bh)
 		brelse(bh);
 	return;
 
- out_badread:
+out_badread:
 	printk(KERN_WARNING "ISOFS: unable to read i-node block\n");
- fail:
+fail:
 	make_bad_inode(inode);
 	goto out;
 }
@@ -1394,11 +1391,8 @@
 
 	hashval = (block << sb->s_blocksize_bits) | offset;
 
-	inode = iget5_locked(sb,
-			     hashval,
-			     &isofs_iget5_test,
-			     &isofs_iget5_set,
-			     &data);
+	inode = iget5_locked(sb, hashval, &isofs_iget5_test,
+			     &isofs_iget5_set, &data);
 
 	if (inode && (inode->i_state & I_NEW)) {
 		sb->s_op->read_inode(inode);
@@ -1408,36 +1402,6 @@
 	return inode;
 }
 
-#ifdef LEAK_CHECK
-#undef malloc
-#undef free_s
-#undef sb_bread
-#undef brelse
-
-void * leak_check_malloc(unsigned int size){
-  void * tmp;
-  check_malloc++;
-  tmp = kmalloc(size, GFP_KERNEL);
-  return tmp;
-}
-
-void leak_check_free_s(void * obj, int size){
-  check_malloc--;
-  return kfree(obj);
-}
-
-struct buffer_head * leak_check_bread(struct super_block *sb, int block){
-  check_bread++;
-  return sb_bread(sb, block);
-}
-
-void leak_check_brelse(struct buffer_head * bh){
-  check_bread--;
-  return brelse(bh);
-}
-
-#endif
-
 static struct super_block *isofs_get_sb(struct file_system_type *fs_type,
 	int flags, const char *dev_name, void *data)
 {
diff --git a/fs/isofs/isofs.h b/fs/isofs/isofs.h
index 9ce7b51..38c7515 100644
--- a/fs/isofs/isofs.h
+++ b/fs/isofs/isofs.h
@@ -47,6 +47,8 @@
 	unsigned char s_nosuid;
 	unsigned char s_nodev;
 	unsigned char s_nocompress;
+	unsigned char s_hide;
+	unsigned char s_showassoc;
 
 	mode_t s_mode;
 	gid_t s_gid;
diff --git a/fs/isofs/namei.c b/fs/isofs/namei.c
index 690edf3..e37e82b 100644
--- a/fs/isofs/namei.c
+++ b/fs/isofs/namei.c
@@ -131,14 +131,16 @@
 		}
 
 		/*
-		 * Skip hidden or associated files unless unhide is set 
+		 * Skip hidden or associated files unless hide or showassoc,
+		 * respectively, is set
 		 */
 		match = 0;
 		if (dlen > 0 &&
-		    (!(de->flags[-sbi->s_high_sierra] & 5)
-		     || sbi->s_unhide == 'y'))
-		{
-			match = (isofs_cmp(dentry,dpnt,dlen) == 0);
+			(sbi->s_hide =='n' ||
+				(!(de->flags[-sbi->s_high_sierra] & 1))) &&
+			(sbi->s_showassoc =='y' ||
+				(!(de->flags[-sbi->s_high_sierra] & 4)))) {
+			match = (isofs_cmp(dentry, dpnt, dlen) == 0);
 		}
 		if (match) {
 			isofs_normalize_block_and_offset(de,
@@ -146,11 +148,11 @@
 							 &offset_saved);
                         *block_rv = block_saved;
                         *offset_rv = offset_saved;
-			if (bh) brelse(bh);
+			brelse(bh);
 			return 1;
 		}
 	}
-	if (bh) brelse(bh);
+	brelse(bh);
 	return 0;
 }
 
diff --git a/fs/isofs/rock.c b/fs/isofs/rock.c
index 089e79c..4326cb4 100644
--- a/fs/isofs/rock.c
+++ b/fs/isofs/rock.c
@@ -13,352 +13,542 @@
 #include "isofs.h"
 #include "rock.h"
 
-/* These functions are designed to read the system areas of a directory record
+/*
+ * These functions are designed to read the system areas of a directory record
  * and extract relevant information.  There are different functions provided
  * depending upon what information we need at the time.  One function fills
  * out an inode structure, a second one extracts a filename, a third one
  * returns a symbolic link name, and a fourth one returns the extent number
- * for the file. */
+ * for the file.
+ */
 
-#define SIG(A,B) ((A) | ((B) << 8)) /* isonum_721() */
+#define SIG(A,B) ((A) | ((B) << 8))	/* isonum_721() */
 
+struct rock_state {
+	void *buffer;
+	unsigned char *chr;
+	int len;
+	int cont_size;
+	int cont_extent;
+	int cont_offset;
+	struct inode *inode;
+};
 
-/* This is a way of ensuring that we have something in the system
-   use fields that is compatible with Rock Ridge */
-#define CHECK_SP(FAIL)	       			\
-      if(rr->u.SP.magic[0] != 0xbe) FAIL;	\
-      if(rr->u.SP.magic[1] != 0xef) FAIL;       \
-      ISOFS_SB(inode->i_sb)->s_rock_offset=rr->u.SP.skip;
-/* We define a series of macros because each function must do exactly the
-   same thing in certain places.  We use the macros to ensure that everything
-   is done correctly */
+/*
+ * This is a way of ensuring that we have something in the system
+ * use fields that is compatible with Rock Ridge.  Return zero on success.
+ */
 
-#define CONTINUE_DECLS \
-  int cont_extent = 0, cont_offset = 0, cont_size = 0;   \
-  void *buffer = NULL
-
-#define CHECK_CE	       			\
-      {cont_extent = isonum_733(rr->u.CE.extent); \
-      cont_offset = isonum_733(rr->u.CE.offset); \
-      cont_size = isonum_733(rr->u.CE.size);}
-
-#define SETUP_ROCK_RIDGE(DE,CHR,LEN)	      		      	\
-  {LEN= sizeof(struct iso_directory_record) + DE->name_len[0];	\
-  if(LEN & 1) LEN++;						\
-  CHR = ((unsigned char *) DE) + LEN;				\
-  LEN = *((unsigned char *) DE) - LEN;                          \
-  if (LEN<0) LEN=0;                                             \
-  if (ISOFS_SB(inode->i_sb)->s_rock_offset!=-1)                \
-  {                                                             \
-     LEN-=ISOFS_SB(inode->i_sb)->s_rock_offset;                \
-     CHR+=ISOFS_SB(inode->i_sb)->s_rock_offset;                \
-     if (LEN<0) LEN=0;                                          \
-  }                                                             \
-}                                     
-
-#define MAYBE_CONTINUE(LABEL,DEV) \
-  {if (buffer) { kfree(buffer); buffer = NULL; } \
-  if (cont_extent){ \
-    int block, offset, offset1; \
-    struct buffer_head * pbh; \
-    buffer = kmalloc(cont_size,GFP_KERNEL); \
-    if (!buffer) goto out; \
-    block = cont_extent; \
-    offset = cont_offset; \
-    offset1 = 0; \
-    pbh = sb_bread(DEV->i_sb, block); \
-    if(pbh){       \
-      if (offset > pbh->b_size || offset + cont_size > pbh->b_size){	\
-	brelse(pbh); \
-	goto out; \
-      } \
-      memcpy(buffer + offset1, pbh->b_data + offset, cont_size - offset1); \
-      brelse(pbh); \
-      chr = (unsigned char *) buffer; \
-      len = cont_size; \
-      cont_extent = 0; \
-      cont_size = 0; \
-      cont_offset = 0; \
-      goto LABEL; \
-    }    \
-    printk("Unable to read rock-ridge attributes\n");    \
-  }}
-
-/* return length of name field; 0: not found, -1: to be ignored */
-int get_rock_ridge_filename(struct iso_directory_record * de,
-			    char * retname, struct inode * inode)
+static int check_sp(struct rock_ridge *rr, struct inode *inode)
 {
-  int len;
-  unsigned char * chr;
-  CONTINUE_DECLS;
-  int retnamlen = 0, truncate=0;
- 
-  if (!ISOFS_SB(inode->i_sb)->s_rock) return 0;
-  *retname = 0;
+	if (rr->u.SP.magic[0] != 0xbe)
+		return -1;
+	if (rr->u.SP.magic[1] != 0xef)
+		return -1;
+	ISOFS_SB(inode->i_sb)->s_rock_offset = rr->u.SP.skip;
+	return 0;
+}
 
-  SETUP_ROCK_RIDGE(de, chr, len);
- repeat:
-  {
-    struct rock_ridge * rr;
-    int sig;
-    
-    while (len > 2){ /* There may be one byte for padding somewhere */
-      rr = (struct rock_ridge *) chr;
-      if (rr->len < 3) goto out; /* Something got screwed up here */
-      sig = isonum_721(chr);
-      chr += rr->len; 
-      len -= rr->len;
-      if (len < 0) goto out;	/* corrupted isofs */
+static void setup_rock_ridge(struct iso_directory_record *de,
+			struct inode *inode, struct rock_state *rs)
+{
+	rs->len = sizeof(struct iso_directory_record) + de->name_len[0];
+	if (rs->len & 1)
+		(rs->len)++;
+	rs->chr = (unsigned char *)de + rs->len;
+	rs->len = *((unsigned char *)de) - rs->len;
+	if (rs->len < 0)
+		rs->len = 0;
 
-      switch(sig){
-      case SIG('R','R'):
-	if((rr->u.RR.flags[0] & RR_NM) == 0) goto out;
-	break;
-      case SIG('S','P'):
-	CHECK_SP(goto out);
-	break;
-      case SIG('C','E'):
-	CHECK_CE;
-	break;
-      case SIG('N','M'):
-	if (truncate) break;
-	if (rr->len < 5) break;
-        /*
-	 * If the flags are 2 or 4, this indicates '.' or '..'.
-	 * We don't want to do anything with this, because it
-	 * screws up the code that calls us.  We don't really
-	 * care anyways, since we can just use the non-RR
-	 * name.
-	 */
-	if (rr->u.NM.flags & 6) {
-	  break;
+	if (ISOFS_SB(inode->i_sb)->s_rock_offset != -1) {
+		rs->len -= ISOFS_SB(inode->i_sb)->s_rock_offset;
+		rs->chr += ISOFS_SB(inode->i_sb)->s_rock_offset;
+		if (rs->len < 0)
+			rs->len = 0;
+	}
+}
+
+static void init_rock_state(struct rock_state *rs, struct inode *inode)
+{
+	memset(rs, 0, sizeof(*rs));
+	rs->inode = inode;
+}
+
+/*
+ * Returns 0 if the caller should continue scanning, 1 if the scan must end
+ * and -ve on error.
+ */
+static int rock_continue(struct rock_state *rs)
+{
+	int ret = 1;
+	int blocksize = 1 << rs->inode->i_blkbits;
+	const int min_de_size = offsetof(struct rock_ridge, u);
+
+	kfree(rs->buffer);
+	rs->buffer = NULL;
+
+	if ((unsigned)rs->cont_offset > blocksize - min_de_size ||
+	    (unsigned)rs->cont_size > blocksize ||
+	    (unsigned)(rs->cont_offset + rs->cont_size) > blocksize) {
+		printk(KERN_NOTICE "rock: corrupted directory entry. "
+			"extent=%d, offset=%d, size=%d\n",
+			rs->cont_extent, rs->cont_offset, rs->cont_size);
+		ret = -EIO;
+		goto out;
 	}
 
-	if (rr->u.NM.flags & ~1) {
-	  printk("Unsupported NM flag settings (%d)\n",rr->u.NM.flags);
-	  break;
+	if (rs->cont_extent) {
+		struct buffer_head *bh;
+
+		rs->buffer = kmalloc(rs->cont_size, GFP_KERNEL);
+		if (!rs->buffer) {
+			ret = -ENOMEM;
+			goto out;
+		}
+		ret = -EIO;
+		bh = sb_bread(rs->inode->i_sb, rs->cont_extent);
+		if (bh) {
+			memcpy(rs->buffer, bh->b_data + rs->cont_offset,
+					rs->cont_size);
+			put_bh(bh);
+			rs->chr = rs->buffer;
+			rs->len = rs->cont_size;
+			rs->cont_extent = 0;
+			rs->cont_size = 0;
+			rs->cont_offset = 0;
+			return 0;
+		}
+		printk("Unable to read rock-ridge attributes\n");
 	}
-	if((strlen(retname) + rr->len - 5) >= 254) {
-	  truncate = 1;
-	  break;
+out:
+	kfree(rs->buffer);
+	rs->buffer = NULL;
+	return ret;
+}
+
+/*
+ * We think there's a record of type `sig' at rs->chr.  Parse the signature
+ * and make sure that there's really room for a record of that type.
+ */
+static int rock_check_overflow(struct rock_state *rs, int sig)
+{
+	int len;
+
+	switch (sig) {
+	case SIG('S', 'P'):
+		len = sizeof(struct SU_SP_s);
+		break;
+	case SIG('C', 'E'):
+		len = sizeof(struct SU_CE_s);
+		break;
+	case SIG('E', 'R'):
+		len = sizeof(struct SU_ER_s);
+		break;
+	case SIG('R', 'R'):
+		len = sizeof(struct RR_RR_s);
+		break;
+	case SIG('P', 'X'):
+		len = sizeof(struct RR_PX_s);
+		break;
+	case SIG('P', 'N'):
+		len = sizeof(struct RR_PN_s);
+		break;
+	case SIG('S', 'L'):
+		len = sizeof(struct RR_SL_s);
+		break;
+	case SIG('N', 'M'):
+		len = sizeof(struct RR_NM_s);
+		break;
+	case SIG('C', 'L'):
+		len = sizeof(struct RR_CL_s);
+		break;
+	case SIG('P', 'L'):
+		len = sizeof(struct RR_PL_s);
+		break;
+	case SIG('T', 'F'):
+		len = sizeof(struct RR_TF_s);
+		break;
+	case SIG('Z', 'F'):
+		len = sizeof(struct RR_ZF_s);
+		break;
+	default:
+		len = 0;
+		break;
 	}
-	strncat(retname, rr->u.NM.name, rr->len - 5);
-	retnamlen += rr->len - 5;
-	break;
-      case SIG('R','E'):
-	if (buffer) kfree(buffer);
-	return -1;
-      default:
-	break;
-      }
-    }
-  }
-  MAYBE_CONTINUE(repeat,inode);
-  if (buffer) kfree(buffer);
-  return retnamlen; /* If 0, this file did not have a NM field */
- out:
-  if(buffer) kfree(buffer);
-  return 0;
+	len += offsetof(struct rock_ridge, u);
+	if (len > rs->len) {
+		printk(KERN_NOTICE "rock: directory entry would overflow "
+				"storage\n");
+		printk(KERN_NOTICE "rock: sig=0x%02x, size=%d, remaining=%d\n",
+				sig, len, rs->len);
+		return -EIO;
+	}
+	return 0;
+}
+
+/*
+ * return length of name field; 0: not found, -1: to be ignored
+ */
+int get_rock_ridge_filename(struct iso_directory_record *de,
+			    char *retname, struct inode *inode)
+{
+	struct rock_state rs;
+	struct rock_ridge *rr;
+	int sig;
+	int retnamlen = 0;
+	int truncate = 0;
+	int ret = 0;
+
+	if (!ISOFS_SB(inode->i_sb)->s_rock)
+		return 0;
+	*retname = 0;
+
+	init_rock_state(&rs, inode);
+	setup_rock_ridge(de, inode, &rs);
+repeat:
+
+	while (rs.len > 2) { /* There may be one byte for padding somewhere */
+		rr = (struct rock_ridge *)rs.chr;
+		if (rr->len < 3)
+			goto out;	/* Something got screwed up here */
+		sig = isonum_721(rs.chr);
+		if (rock_check_overflow(&rs, sig))
+			goto eio;
+		rs.chr += rr->len;
+		rs.len -= rr->len;
+		if (rs.len < 0)
+			goto eio;	/* corrupted isofs */
+
+		switch (sig) {
+		case SIG('R', 'R'):
+			if ((rr->u.RR.flags[0] & RR_NM) == 0)
+				goto out;
+			break;
+		case SIG('S', 'P'):
+			if (check_sp(rr, inode))
+				goto out;
+			break;
+		case SIG('C', 'E'):
+			rs.cont_extent = isonum_733(rr->u.CE.extent);
+			rs.cont_offset = isonum_733(rr->u.CE.offset);
+			rs.cont_size = isonum_733(rr->u.CE.size);
+			break;
+		case SIG('N', 'M'):
+			if (truncate)
+				break;
+			if (rr->len < 5)
+				break;
+			/*
+			 * If the flags are 2 or 4, this indicates '.' or '..'.
+			 * We don't want to do anything with this, because it
+			 * screws up the code that calls us.  We don't really
+			 * care anyways, since we can just use the non-RR
+			 * name.
+			 */
+			if (rr->u.NM.flags & 6)
+				break;
+
+			if (rr->u.NM.flags & ~1) {
+				printk("Unsupported NM flag settings (%d)\n",
+					rr->u.NM.flags);
+				break;
+			}
+			if ((strlen(retname) + rr->len - 5) >= 254) {
+				truncate = 1;
+				break;
+			}
+			strncat(retname, rr->u.NM.name, rr->len - 5);
+			retnamlen += rr->len - 5;
+			break;
+		case SIG('R', 'E'):
+			kfree(rs.buffer);
+			return -1;
+		default:
+			break;
+		}
+	}
+	ret = rock_continue(&rs);
+	if (ret == 0)
+		goto repeat;
+	if (ret == 1)
+		return retnamlen; /* If 0, this file did not have a NM field */
+out:
+	kfree(rs.buffer);
+	return ret;
+eio:
+	ret = -EIO;
+	goto out;
 }
 
 static int
 parse_rock_ridge_inode_internal(struct iso_directory_record *de,
 				struct inode *inode, int regard_xa)
 {
-  int len;
-  unsigned char * chr;
-  int symlink_len = 0;
-  CONTINUE_DECLS;
+	int symlink_len = 0;
+	int cnt, sig;
+	struct inode *reloc;
+	struct rock_ridge *rr;
+	int rootflag;
+	struct rock_state rs;
+	int ret = 0;
 
-  if (!ISOFS_SB(inode->i_sb)->s_rock) return 0;
+	if (!ISOFS_SB(inode->i_sb)->s_rock)
+		return 0;
 
-  SETUP_ROCK_RIDGE(de, chr, len);
-  if (regard_xa)
-   {
-     chr+=14;
-     len-=14;
-     if (len<0) len=0;
-   }
-   
- repeat:
-  {
-    int cnt, sig;
-    struct inode * reloc;
-    struct rock_ridge * rr;
-    int rootflag;
-    
-    while (len > 2){ /* There may be one byte for padding somewhere */
-      rr = (struct rock_ridge *) chr;
-      if (rr->len < 3) goto out; /* Something got screwed up here */
-      sig = isonum_721(chr);
-      chr += rr->len; 
-      len -= rr->len;
-      if (len < 0) goto out;	/* corrupted isofs */
-      
-      switch(sig){
+	init_rock_state(&rs, inode);
+	setup_rock_ridge(de, inode, &rs);
+	if (regard_xa) {
+		rs.chr += 14;
+		rs.len -= 14;
+		if (rs.len < 0)
+			rs.len = 0;
+	}
+
+repeat:
+	while (rs.len > 2) { /* There may be one byte for padding somewhere */
+		rr = (struct rock_ridge *)rs.chr;
+		if (rr->len < 3)
+			goto out;	/* Something got screwed up here */
+		sig = isonum_721(rs.chr);
+		if (rock_check_overflow(&rs, sig))
+			goto eio;
+		rs.chr += rr->len;
+		rs.len -= rr->len;
+		if (rs.len < 0)
+			goto eio;	/* corrupted isofs */
+
+		switch (sig) {
 #ifndef CONFIG_ZISOFS		/* No flag for SF or ZF */
-      case SIG('R','R'):
-	if((rr->u.RR.flags[0] & 
- 	    (RR_PX | RR_TF | RR_SL | RR_CL)) == 0) goto out;
-	break;
+		case SIG('R', 'R'):
+			if ((rr->u.RR.flags[0] &
+			     (RR_PX | RR_TF | RR_SL | RR_CL)) == 0)
+				goto out;
+			break;
 #endif
-      case SIG('S','P'):
-	CHECK_SP(goto out);
-	break;
-      case SIG('C','E'):
-	CHECK_CE;
-	break;
-      case SIG('E','R'):
-	ISOFS_SB(inode->i_sb)->s_rock = 1;
-	printk(KERN_DEBUG "ISO 9660 Extensions: ");
-	{ int p;
-	  for(p=0;p<rr->u.ER.len_id;p++) printk("%c",rr->u.ER.data[p]);
-	}
-	  printk("\n");
-	break;
-      case SIG('P','X'):
-	inode->i_mode  = isonum_733(rr->u.PX.mode);
-	inode->i_nlink = isonum_733(rr->u.PX.n_links);
-	inode->i_uid   = isonum_733(rr->u.PX.uid);
-	inode->i_gid   = isonum_733(rr->u.PX.gid);
-	break;
-      case SIG('P','N'):
-	{ int high, low;
-	  high = isonum_733(rr->u.PN.dev_high);
-	  low = isonum_733(rr->u.PN.dev_low);
-	  /*
-	   * The Rock Ridge standard specifies that if sizeof(dev_t) <= 4,
-	   * then the high field is unused, and the device number is completely
-	   * stored in the low field.  Some writers may ignore this subtlety,
-	   * and as a result we test to see if the entire device number is
-	   * stored in the low field, and use that.
-	   */
-	  if((low & ~0xff) && high == 0) {
-	    inode->i_rdev = MKDEV(low >> 8, low & 0xff);
-	  } else {
-	    inode->i_rdev = MKDEV(high, low);
-	  }
-	}
-	break;
-      case SIG('T','F'):
-	/* Some RRIP writers incorrectly place ctime in the TF_CREATE field.
-	   Try to handle this correctly for either case. */
-	cnt = 0; /* Rock ridge never appears on a High Sierra disk */
-	if(rr->u.TF.flags & TF_CREATE) { 
-	  inode->i_ctime.tv_sec = iso_date(rr->u.TF.times[cnt++].time, 0);
-	  inode->i_ctime.tv_nsec = 0;
-	}
-	if(rr->u.TF.flags & TF_MODIFY) {
-	  inode->i_mtime.tv_sec = iso_date(rr->u.TF.times[cnt++].time, 0);
-	  inode->i_mtime.tv_nsec = 0;
-	}
-	if(rr->u.TF.flags & TF_ACCESS) {
-	  inode->i_atime.tv_sec = iso_date(rr->u.TF.times[cnt++].time, 0);
-	  inode->i_atime.tv_nsec = 0;
-	}
-	if(rr->u.TF.flags & TF_ATTRIBUTES) { 
-	  inode->i_ctime.tv_sec = iso_date(rr->u.TF.times[cnt++].time, 0);
-	  inode->i_ctime.tv_nsec = 0;
-	} 
-	break;
-      case SIG('S','L'):
-	{int slen;
-	 struct SL_component * slp;
-	 struct SL_component * oldslp;
-	 slen = rr->len - 5;
-	 slp = &rr->u.SL.link;
-	 inode->i_size = symlink_len;
-	 while (slen > 1){
-	   rootflag = 0;
-	   switch(slp->flags &~1){
-	   case 0:
-	     inode->i_size += slp->len;
-	     break;
-	   case 2:
-	     inode->i_size += 1;
-	     break;
-	   case 4:
-	     inode->i_size += 2;
-	     break;
-	   case 8:
-	     rootflag = 1;
-	     inode->i_size += 1;
-	     break;
-	   default:
-	     printk("Symlink component flag not implemented\n");
-	   }
-	   slen -= slp->len + 2;
-	   oldslp = slp;
-	   slp = (struct SL_component *) (((char *) slp) + slp->len + 2);
+		case SIG('S', 'P'):
+			if (check_sp(rr, inode))
+				goto out;
+			break;
+		case SIG('C', 'E'):
+			rs.cont_extent = isonum_733(rr->u.CE.extent);
+			rs.cont_offset = isonum_733(rr->u.CE.offset);
+			rs.cont_size = isonum_733(rr->u.CE.size);
+			break;
+		case SIG('E', 'R'):
+			ISOFS_SB(inode->i_sb)->s_rock = 1;
+			printk(KERN_DEBUG "ISO 9660 Extensions: ");
+			{
+				int p;
+				for (p = 0; p < rr->u.ER.len_id; p++)
+					printk("%c", rr->u.ER.data[p]);
+			}
+			printk("\n");
+			break;
+		case SIG('P', 'X'):
+			inode->i_mode = isonum_733(rr->u.PX.mode);
+			inode->i_nlink = isonum_733(rr->u.PX.n_links);
+			inode->i_uid = isonum_733(rr->u.PX.uid);
+			inode->i_gid = isonum_733(rr->u.PX.gid);
+			break;
+		case SIG('P', 'N'):
+			{
+				int high, low;
+				high = isonum_733(rr->u.PN.dev_high);
+				low = isonum_733(rr->u.PN.dev_low);
+				/*
+				 * The Rock Ridge standard specifies that if
+				 * sizeof(dev_t) <= 4, then the high field is
+				 * unused, and the device number is completely
+				 * stored in the low field.  Some writers may
+				 * ignore this subtlety,
+				 * and as a result we test to see if the entire
+				 * device number is
+				 * stored in the low field, and use that.
+				 */
+				if ((low & ~0xff) && high == 0) {
+					inode->i_rdev =
+					    MKDEV(low >> 8, low & 0xff);
+				} else {
+					inode->i_rdev =
+					    MKDEV(high, low);
+				}
+			}
+			break;
+		case SIG('T', 'F'):
+			/*
+			 * Some RRIP writers incorrectly place ctime in the
+			 * TF_CREATE field. Try to handle this correctly for
+			 * either case.
+			 */
+			/* Rock ridge never appears on a High Sierra disk */
+			cnt = 0;
+			if (rr->u.TF.flags & TF_CREATE) {
+				inode->i_ctime.tv_sec =
+				    iso_date(rr->u.TF.times[cnt++].time,
+					     0);
+				inode->i_ctime.tv_nsec = 0;
+			}
+			if (rr->u.TF.flags & TF_MODIFY) {
+				inode->i_mtime.tv_sec =
+				    iso_date(rr->u.TF.times[cnt++].time,
+					     0);
+				inode->i_mtime.tv_nsec = 0;
+			}
+			if (rr->u.TF.flags & TF_ACCESS) {
+				inode->i_atime.tv_sec =
+				    iso_date(rr->u.TF.times[cnt++].time,
+					     0);
+				inode->i_atime.tv_nsec = 0;
+			}
+			if (rr->u.TF.flags & TF_ATTRIBUTES) {
+				inode->i_ctime.tv_sec =
+				    iso_date(rr->u.TF.times[cnt++].time,
+					     0);
+				inode->i_ctime.tv_nsec = 0;
+			}
+			break;
+		case SIG('S', 'L'):
+			{
+				int slen;
+				struct SL_component *slp;
+				struct SL_component *oldslp;
+				slen = rr->len - 5;
+				slp = &rr->u.SL.link;
+				inode->i_size = symlink_len;
+				while (slen > 1) {
+					rootflag = 0;
+					switch (slp->flags & ~1) {
+					case 0:
+						inode->i_size +=
+						    slp->len;
+						break;
+					case 2:
+						inode->i_size += 1;
+						break;
+					case 4:
+						inode->i_size += 2;
+						break;
+					case 8:
+						rootflag = 1;
+						inode->i_size += 1;
+						break;
+					default:
+						printk("Symlink component flag "
+							"not implemented\n");
+					}
+					slen -= slp->len + 2;
+					oldslp = slp;
+					slp = (struct SL_component *)
+						(((char *)slp) + slp->len + 2);
 
-	   if(slen < 2) {
-	     if(    ((rr->u.SL.flags & 1) != 0) 
-		    && ((oldslp->flags & 1) == 0) ) inode->i_size += 1;
-	     break;
-	   }
+					if (slen < 2) {
+						if (((rr->u.SL.
+						      flags & 1) != 0)
+						    &&
+						    ((oldslp->
+						      flags & 1) == 0))
+							inode->i_size +=
+							    1;
+						break;
+					}
 
-	   /*
-	    * If this component record isn't continued, then append a '/'.
-	    */
-	   if (!rootflag && (oldslp->flags & 1) == 0)
-		   inode->i_size += 1;
-	 }
-	}
-	symlink_len = inode->i_size;
-	break;
-      case SIG('R','E'):
-	printk(KERN_WARNING "Attempt to read inode for relocated directory\n");
-	goto out;
-      case SIG('C','L'):
-	ISOFS_I(inode)->i_first_extent = isonum_733(rr->u.CL.location);
-	reloc = isofs_iget(inode->i_sb, ISOFS_I(inode)->i_first_extent, 0);
-	if (!reloc)
-		goto out;
-	inode->i_mode = reloc->i_mode;
-	inode->i_nlink = reloc->i_nlink;
-	inode->i_uid = reloc->i_uid;
-	inode->i_gid = reloc->i_gid;
-	inode->i_rdev = reloc->i_rdev;
-	inode->i_size = reloc->i_size;
-	inode->i_blocks = reloc->i_blocks;
-	inode->i_atime = reloc->i_atime;
-	inode->i_ctime = reloc->i_ctime;
-	inode->i_mtime = reloc->i_mtime;
-	iput(reloc);
-	break;
+					/*
+					 * If this component record isn't
+					 * continued, then append a '/'.
+					 */
+					if (!rootflag
+					    && (oldslp->flags & 1) == 0)
+						inode->i_size += 1;
+				}
+			}
+			symlink_len = inode->i_size;
+			break;
+		case SIG('R', 'E'):
+			printk(KERN_WARNING "Attempt to read inode for "
+					"relocated directory\n");
+			goto out;
+		case SIG('C', 'L'):
+			ISOFS_I(inode)->i_first_extent =
+			    isonum_733(rr->u.CL.location);
+			reloc =
+			    isofs_iget(inode->i_sb,
+				       ISOFS_I(inode)->i_first_extent,
+				       0);
+			if (!reloc)
+				goto out;
+			inode->i_mode = reloc->i_mode;
+			inode->i_nlink = reloc->i_nlink;
+			inode->i_uid = reloc->i_uid;
+			inode->i_gid = reloc->i_gid;
+			inode->i_rdev = reloc->i_rdev;
+			inode->i_size = reloc->i_size;
+			inode->i_blocks = reloc->i_blocks;
+			inode->i_atime = reloc->i_atime;
+			inode->i_ctime = reloc->i_ctime;
+			inode->i_mtime = reloc->i_mtime;
+			iput(reloc);
+			break;
 #ifdef CONFIG_ZISOFS
-      case SIG('Z','F'):
-	      if ( !ISOFS_SB(inode->i_sb)->s_nocompress ) {
-		      int algo;
-		      algo = isonum_721(rr->u.ZF.algorithm);
-		      if ( algo == SIG('p','z') ) {
-			      int block_shift = isonum_711(&rr->u.ZF.parms[1]);
-			      if ( block_shift < PAGE_CACHE_SHIFT || block_shift > 17 ) {
-				      printk(KERN_WARNING "isofs: Can't handle ZF block size of 2^%d\n", block_shift);
-			      } else {
-				/* Note: we don't change i_blocks here */
-				      ISOFS_I(inode)->i_file_format = isofs_file_compressed;
-				/* Parameters to compression algorithm (header size, block size) */
-				      ISOFS_I(inode)->i_format_parm[0] = isonum_711(&rr->u.ZF.parms[0]);
-				      ISOFS_I(inode)->i_format_parm[1] = isonum_711(&rr->u.ZF.parms[1]);
-				      inode->i_size = isonum_733(rr->u.ZF.real_size);
-			      }
-		      } else {
-			      printk(KERN_WARNING "isofs: Unknown ZF compression algorithm: %c%c\n",
-				     rr->u.ZF.algorithm[0], rr->u.ZF.algorithm[1]);
-		      }
-	      }
-	      break;
+		case SIG('Z', 'F'): {
+			int algo;
+
+			if (ISOFS_SB(inode->i_sb)->s_nocompress)
+				break;
+			algo = isonum_721(rr->u.ZF.algorithm);
+			if (algo == SIG('p', 'z')) {
+				int block_shift =
+					isonum_711(&rr->u.ZF.parms[1]);
+				if (block_shift < PAGE_CACHE_SHIFT
+						|| block_shift > 17) {
+					printk(KERN_WARNING "isofs: "
+						"Can't handle ZF block "
+						"size of 2^%d\n",
+						block_shift);
+				} else {
+					/*
+					 * Note: we don't change
+					 * i_blocks here
+					 */
+					ISOFS_I(inode)->i_file_format =
+						isofs_file_compressed;
+					/*
+					 * Parameters to compression
+					 * algorithm (header size,
+					 * block size)
+					 */
+					ISOFS_I(inode)->i_format_parm[0] =
+						isonum_711(&rr->u.ZF.parms[0]);
+					ISOFS_I(inode)->i_format_parm[1] =
+						isonum_711(&rr->u.ZF.parms[1]);
+					inode->i_size =
+					    isonum_733(rr->u.ZF.
+						       real_size);
+				}
+			} else {
+				printk(KERN_WARNING
+				       "isofs: Unknown ZF compression "
+						"algorithm: %c%c\n",
+				       rr->u.ZF.algorithm[0],
+				       rr->u.ZF.algorithm[1]);
+			}
+			break;
+		}
 #endif
-      default:
-	break;
-      }
-    }
-  }
-  MAYBE_CONTINUE(repeat,inode);
- out:
-  if(buffer) kfree(buffer);
-  return 0;
+		default:
+			break;
+		}
+	}
+	ret = rock_continue(&rs);
+	if (ret == 0)
+		goto repeat;
+	if (ret == 1)
+		ret = 0;
+out:
+	kfree(rs.buffer);
+	return ret;
+eio:
+	ret = -EIO;
+	goto out;
 }
 
 static char *get_symlink_chunk(char *rpnt, struct rock_ridge *rr, char *plimit)
@@ -376,32 +566,32 @@
 			if (slp->len > plimit - rpnt)
 				return NULL;
 			memcpy(rpnt, slp->text, slp->len);
-			rpnt+=slp->len;
+			rpnt += slp->len;
 			break;
 		case 2:
 			if (rpnt >= plimit)
 				return NULL;
-			*rpnt++='.';
+			*rpnt++ = '.';
 			break;
 		case 4:
 			if (2 > plimit - rpnt)
 				return NULL;
-			*rpnt++='.';
-			*rpnt++='.';
+			*rpnt++ = '.';
+			*rpnt++ = '.';
 			break;
 		case 8:
 			if (rpnt >= plimit)
 				return NULL;
 			rootflag = 1;
-			*rpnt++='/';
+			*rpnt++ = '/';
 			break;
 		default:
 			printk("Symlink component flag not implemented (%d)\n",
-			     slp->flags);
+			       slp->flags);
 		}
 		slen -= slp->len + 2;
 		oldslp = slp;
-		slp = (struct SL_component *) ((char *) slp + slp->len + 2);
+		slp = (struct SL_component *)((char *)slp + slp->len + 2);
 
 		if (slen < 2) {
 			/*
@@ -412,7 +602,7 @@
 			    !(oldslp->flags & 1)) {
 				if (rpnt >= plimit)
 					return NULL;
-				*rpnt++='/';
+				*rpnt++ = '/';
 			}
 			break;
 		}
@@ -423,59 +613,61 @@
 		if (!rootflag && !(oldslp->flags & 1)) {
 			if (rpnt >= plimit)
 				return NULL;
-			*rpnt++='/';
+			*rpnt++ = '/';
 		}
 	}
 	return rpnt;
 }
 
-int parse_rock_ridge_inode(struct iso_directory_record * de,
-			   struct inode * inode)
+int parse_rock_ridge_inode(struct iso_directory_record *de, struct inode *inode)
 {
-   int result=parse_rock_ridge_inode_internal(de,inode,0);
-   /* if rockridge flag was reset and we didn't look for attributes
-    * behind eventual XA attributes, have a look there */
-   if ((ISOFS_SB(inode->i_sb)->s_rock_offset==-1)
-       &&(ISOFS_SB(inode->i_sb)->s_rock==2))
-     {
-	result=parse_rock_ridge_inode_internal(de,inode,14);
-     }
-   return result;
+	int result = parse_rock_ridge_inode_internal(de, inode, 0);
+
+	/*
+	 * if rockridge flag was reset and we didn't look for attributes
+	 * behind eventual XA attributes, have a look there
+	 */
+	if ((ISOFS_SB(inode->i_sb)->s_rock_offset == -1)
+	    && (ISOFS_SB(inode->i_sb)->s_rock == 2)) {
+		result = parse_rock_ridge_inode_internal(de, inode, 14);
+	}
+	return result;
 }
 
-/* readpage() for symlinks: reads symlink contents into the page and either
-   makes it uptodate and returns 0 or returns error (-EIO) */
-
+/*
+ * readpage() for symlinks: reads symlink contents into the page and either
+ * makes it uptodate and returns 0 or returns error (-EIO)
+ */
 static int rock_ridge_symlink_readpage(struct file *file, struct page *page)
 {
 	struct inode *inode = page->mapping->host;
-        struct iso_inode_info *ei = ISOFS_I(inode);
+	struct iso_inode_info *ei = ISOFS_I(inode);
 	char *link = kmap(page);
 	unsigned long bufsize = ISOFS_BUFFER_SIZE(inode);
 	struct buffer_head *bh;
 	char *rpnt = link;
 	unsigned char *pnt;
-	struct iso_directory_record *raw_inode;
-	CONTINUE_DECLS;
+	struct iso_directory_record *raw_de;
 	unsigned long block, offset;
 	int sig;
-	int len;
-	unsigned char *chr;
 	struct rock_ridge *rr;
+	struct rock_state rs;
+	int ret;
 
 	if (!ISOFS_SB(inode->i_sb)->s_rock)
 		goto error;
 
+	init_rock_state(&rs, inode);
 	block = ei->i_iget5_block;
 	lock_kernel();
 	bh = sb_bread(inode->i_sb, block);
 	if (!bh)
 		goto out_noread;
 
-        offset = ei->i_iget5_offset;
-	pnt = (unsigned char *) bh->b_data + offset;
+	offset = ei->i_iget5_offset;
+	pnt = (unsigned char *)bh->b_data + offset;
 
-	raw_inode = (struct iso_directory_record *) pnt;
+	raw_de = (struct iso_directory_record *)pnt;
 
 	/*
 	 * If we go past the end of the buffer, there is some sort of error.
@@ -483,20 +675,24 @@
 	if (offset + *pnt > bufsize)
 		goto out_bad_span;
 
-	/* Now test for possible Rock Ridge extensions which will override
-	   some of these numbers in the inode structure. */
+	/*
+	 * Now test for possible Rock Ridge extensions which will override
+	 * some of these numbers in the inode structure.
+	 */
 
-	SETUP_ROCK_RIDGE(raw_inode, chr, len);
+	setup_rock_ridge(raw_de, inode, &rs);
 
-      repeat:
-	while (len > 2) { /* There may be one byte for padding somewhere */
-		rr = (struct rock_ridge *) chr;
+repeat:
+	while (rs.len > 2) { /* There may be one byte for padding somewhere */
+		rr = (struct rock_ridge *)rs.chr;
 		if (rr->len < 3)
 			goto out;	/* Something got screwed up here */
-		sig = isonum_721(chr);
-		chr += rr->len;
-		len -= rr->len;
-		if (len < 0)
+		sig = isonum_721(rs.chr);
+		if (rock_check_overflow(&rs, sig))
+			goto out;
+		rs.chr += rr->len;
+		rs.len -= rr->len;
+		if (rs.len < 0)
 			goto out;	/* corrupted isofs */
 
 		switch (sig) {
@@ -505,7 +701,8 @@
 				goto out;
 			break;
 		case SIG('S', 'P'):
-			CHECK_SP(goto out);
+			if (check_sp(rr, inode))
+				goto out;
 			break;
 		case SIG('S', 'L'):
 			rpnt = get_symlink_chunk(rpnt, rr,
@@ -515,14 +712,18 @@
 			break;
 		case SIG('C', 'E'):
 			/* This tells is if there is a continuation record */
-			CHECK_CE;
+			rs.cont_extent = isonum_733(rr->u.CE.extent);
+			rs.cont_offset = isonum_733(rr->u.CE.offset);
+			rs.cont_size = isonum_733(rr->u.CE.size);
 		default:
 			break;
 		}
 	}
-	MAYBE_CONTINUE(repeat, inode);
-	if (buffer)
-		kfree(buffer);
+	ret = rock_continue(&rs);
+	if (ret == 0)
+		goto repeat;
+	if (ret < 0)
+		goto fail;
 
 	if (rpnt == link)
 		goto fail;
@@ -535,19 +736,18 @@
 	return 0;
 
 	/* error exit from macro */
-      out:
-	if (buffer)
-		kfree(buffer);
+out:
+	kfree(rs.buffer);
 	goto fail;
-      out_noread:
+out_noread:
 	printk("unable to read i-node block");
 	goto fail;
-      out_bad_span:
+out_bad_span:
 	printk("symlink spans iso9660 blocks\n");
-      fail:
+fail:
 	brelse(bh);
 	unlock_kernel();
-      error:
+error:
 	SetPageError(page);
 	kunmap(page);
 	unlock_page(page);
@@ -555,5 +755,5 @@
 }
 
 struct address_space_operations isofs_symlink_aops = {
-	.readpage	= rock_ridge_symlink_readpage
+	.readpage = rock_ridge_symlink_readpage
 };
diff --git a/fs/isofs/rock.h b/fs/isofs/rock.h
index deaf5c8..ed09e2b 100644
--- a/fs/isofs/rock.h
+++ b/fs/isofs/rock.h
@@ -1,85 +1,88 @@
-/* These structs are used by the system-use-sharing protocol, in which the
-   Rock Ridge extensions are embedded.  It is quite possible that other
-   extensions are present on the disk, and this is fine as long as they
-   all use SUSP */
+/*
+ * These structs are used by the system-use-sharing protocol, in which the
+ * Rock Ridge extensions are embedded.  It is quite possible that other
+ * extensions are present on the disk, and this is fine as long as they
+ * all use SUSP
+ */
 
-struct SU_SP{
-  unsigned char magic[2];
-  unsigned char skip;
-} __attribute__((packed));
+struct SU_SP_s {
+	unsigned char magic[2];
+	unsigned char skip;
+} __attribute__ ((packed));
 
-struct SU_CE{
-  char extent[8];
-  char offset[8];
-  char size[8];
+struct SU_CE_s {
+	char extent[8];
+	char offset[8];
+	char size[8];
 };
 
-struct SU_ER{
-  unsigned char len_id;
-  unsigned char len_des;
-  unsigned char len_src;
-  unsigned char ext_ver;
-  char data[0];
-} __attribute__((packed));
+struct SU_ER_s {
+	unsigned char len_id;
+	unsigned char len_des;
+	unsigned char len_src;
+	unsigned char ext_ver;
+	char data[0];
+} __attribute__ ((packed));
 
-struct RR_RR{
-  char flags[1];
-} __attribute__((packed));
+struct RR_RR_s {
+	char flags[1];
+} __attribute__ ((packed));
 
-struct RR_PX{
-  char mode[8];
-  char n_links[8];
-  char uid[8];
-  char gid[8];
+struct RR_PX_s {
+	char mode[8];
+	char n_links[8];
+	char uid[8];
+	char gid[8];
 };
 
-struct RR_PN{
-  char dev_high[8];
-  char dev_low[8];
+struct RR_PN_s {
+	char dev_high[8];
+	char dev_low[8];
 };
 
+struct SL_component {
+	unsigned char flags;
+	unsigned char len;
+	char text[0];
+} __attribute__ ((packed));
 
-struct SL_component{
-  unsigned char flags;
-  unsigned char len;
-  char text[0];
-} __attribute__((packed));
+struct RR_SL_s {
+	unsigned char flags;
+	struct SL_component link;
+} __attribute__ ((packed));
 
-struct RR_SL{
-  unsigned char flags;
-  struct SL_component link;
-} __attribute__((packed));
+struct RR_NM_s {
+	unsigned char flags;
+	char name[0];
+} __attribute__ ((packed));
 
-struct RR_NM{
-  unsigned char flags;
-  char name[0];
-} __attribute__((packed));
-
-struct RR_CL{
-  char location[8];
+struct RR_CL_s {
+	char location[8];
 };
 
-struct RR_PL{
-  char location[8];
+struct RR_PL_s {
+	char location[8];
 };
 
-struct stamp{
-  char time[7];
-} __attribute__((packed));
+struct stamp {
+	char time[7];
+} __attribute__ ((packed));
 
-struct RR_TF{
-  char flags;
-  struct stamp times[0];  /* Variable number of these beasts */
-} __attribute__((packed));
+struct RR_TF_s {
+	char flags;
+	struct stamp times[0];	/* Variable number of these beasts */
+} __attribute__ ((packed));
 
 /* Linux-specific extension for transparent decompression */
-struct RR_ZF{
-  char algorithm[2];
-  char parms[2];
-  char real_size[8];
+struct RR_ZF_s {
+	char algorithm[2];
+	char parms[2];
+	char real_size[8];
 };
 
-/* These are the bits and their meanings for flags in the TF structure. */
+/*
+ * These are the bits and their meanings for flags in the TF structure.
+ */
 #define TF_CREATE 1
 #define TF_MODIFY 2
 #define TF_ACCESS 4
@@ -89,31 +92,31 @@
 #define TF_EFFECTIVE 64
 #define TF_LONG_FORM 128
 
-struct rock_ridge{
-  char signature[2];
-  unsigned char len;
-  unsigned char version;
-  union{
-    struct SU_SP SP;
-    struct SU_CE CE;
-    struct SU_ER ER;
-    struct RR_RR RR;
-    struct RR_PX PX;
-    struct RR_PN PN;
-    struct RR_SL SL;
-    struct RR_NM NM;
-    struct RR_CL CL;
-    struct RR_PL PL;
-    struct RR_TF TF;
-    struct RR_ZF ZF;
-  } u;
+struct rock_ridge {
+	char signature[2];
+	unsigned char len;
+	unsigned char version;
+	union {
+		struct SU_SP_s SP;
+		struct SU_CE_s CE;
+		struct SU_ER_s ER;
+		struct RR_RR_s RR;
+		struct RR_PX_s PX;
+		struct RR_PN_s PN;
+		struct RR_SL_s SL;
+		struct RR_NM_s NM;
+		struct RR_CL_s CL;
+		struct RR_PL_s PL;
+		struct RR_TF_s TF;
+		struct RR_ZF_s ZF;
+	} u;
 };
 
-#define RR_PX 1   /* POSIX attributes */
-#define RR_PN 2   /* POSIX devices */
-#define RR_SL 4   /* Symbolic link */
-#define RR_NM 8   /* Alternate Name */
-#define RR_CL 16  /* Child link */
-#define RR_PL 32  /* Parent link */
-#define RR_RE 64  /* Relocation directory */
-#define RR_TF 128 /* Timestamps */
+#define RR_PX 1			/* POSIX attributes */
+#define RR_PN 2			/* POSIX devices */
+#define RR_SL 4			/* Symbolic link */
+#define RR_NM 8			/* Alternate Name */
+#define RR_CL 16		/* Child link */
+#define RR_PL 32		/* Parent link */
+#define RR_RE 64		/* Relocation directory */
+#define RR_TF 128		/* Timestamps */
diff --git a/fs/jfs/acl.c b/fs/jfs/acl.c
index 8d2a9ab..30a2bf9 100644
--- a/fs/jfs/acl.c
+++ b/fs/jfs/acl.c
@@ -70,8 +70,7 @@
 		if (!IS_ERR(acl))
 			*p_acl = posix_acl_dup(acl);
 	}
-	if (value)
-		kfree(value);
+	kfree(value);
 	return acl;
 }
 
@@ -112,8 +111,7 @@
 	}
 	rc = __jfs_setxattr(inode, ea_name, value, size, 0);
 out:
-	if (value)
-		kfree(value);
+	kfree(value);
 
 	if (!rc) {
 		if (*p_acl && (*p_acl != JFS_ACL_NOT_CACHED))
diff --git a/fs/jfs/file.c b/fs/jfs/file.c
index a87b06f..c2c19c9 100644
--- a/fs/jfs/file.c
+++ b/fs/jfs/file.c
@@ -1,6 +1,6 @@
 /*
- *   Copyright (c) International Business Machines Corp., 2000-2002
- *   Portions Copyright (c) Christoph Hellwig, 2001-2002
+ *   Copyright (C) International Business Machines Corp., 2000-2002
+ *   Portions Copyright (C) Christoph Hellwig, 2001-2002
  *
  *   This program is free software;  you can redistribute it and/or modify
  *   it under the terms of the GNU General Public License as published by
@@ -19,16 +19,13 @@
 
 #include <linux/fs.h>
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_dmap.h"
 #include "jfs_txnmgr.h"
 #include "jfs_xattr.h"
 #include "jfs_acl.h"
 #include "jfs_debug.h"
 
-
-extern int jfs_commit_inode(struct inode *, int);
-extern void jfs_truncate(struct inode *);
-
 int jfs_fsync(struct file *file, struct dentry *dentry, int datasync)
 {
 	struct inode *inode = dentry->d_inode;
diff --git a/fs/jfs/inode.c b/fs/jfs/inode.c
index 24a6891..2137138 100644
--- a/fs/jfs/inode.c
+++ b/fs/jfs/inode.c
@@ -23,6 +23,7 @@
 #include <linux/pagemap.h>
 #include <linux/quotaops.h>
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_filsys.h"
 #include "jfs_imap.h"
 #include "jfs_extent.h"
@@ -30,14 +31,6 @@
 #include "jfs_debug.h"
 
 
-extern struct inode_operations jfs_dir_inode_operations;
-extern struct inode_operations jfs_file_inode_operations;
-extern struct inode_operations jfs_symlink_inode_operations;
-extern struct file_operations jfs_dir_operations;
-extern struct file_operations jfs_file_operations;
-struct address_space_operations jfs_aops;
-extern int freeZeroLink(struct inode *);
-
 void jfs_read_inode(struct inode *inode)
 {
 	if (diRead(inode)) { 
@@ -136,7 +129,7 @@
 	jfs_info("In jfs_delete_inode, inode = 0x%p", inode);
 
 	if (test_cflag(COMMIT_Freewmap, inode))
-		freeZeroLink(inode);
+		jfs_free_zero_link(inode);
 
 	diFree(inode);
 
diff --git a/fs/jfs/jfs_debug.c b/fs/jfs/jfs_debug.c
index 91a0a88..4caea6b 100644
--- a/fs/jfs/jfs_debug.c
+++ b/fs/jfs/jfs_debug.c
@@ -58,8 +58,6 @@
 
 static struct proc_dir_entry *base;
 #ifdef CONFIG_JFS_DEBUG
-extern read_proc_t jfs_txanchor_read;
-
 static int loglevel_read(char *page, char **start, off_t off,
 			 int count, int *eof, void *data)
 {
@@ -97,14 +95,6 @@
 }
 #endif
 
-
-#ifdef CONFIG_JFS_STATISTICS
-extern read_proc_t jfs_lmstats_read;
-extern read_proc_t jfs_txstats_read;
-extern read_proc_t jfs_xtstat_read;
-extern read_proc_t jfs_mpstat_read;
-#endif
-
 static struct {
 	const char	*name;
 	read_proc_t	*read_fn;
diff --git a/fs/jfs/jfs_debug.h b/fs/jfs/jfs_debug.h
index a38079a..ddffbbd 100644
--- a/fs/jfs/jfs_debug.h
+++ b/fs/jfs/jfs_debug.h
@@ -1,6 +1,6 @@
 /*
- *   Copyright (c) International Business Machines Corp., 2000-2002
- *   Portions Copyright (c) Christoph Hellwig, 2001-2002
+ *   Copyright (C) International Business Machines Corp., 2000-2002
+ *   Portions Copyright (C) Christoph Hellwig, 2001-2002
  *
  *   This program is free software;  you can redistribute it and/or modify
  *   it under the terms of the GNU General Public License as published by
@@ -31,7 +31,9 @@
  * CONFIG_JFS_DEBUG or CONFIG_JFS_STATISTICS is defined
  */
 #if defined(CONFIG_PROC_FS) && (defined(CONFIG_JFS_DEBUG) || defined(CONFIG_JFS_STATISTICS))
-	#define PROC_FS_JFS
+#define PROC_FS_JFS
+extern void jfs_proc_init(void);
+extern void jfs_proc_clean(void);
 #endif
 
 /*
@@ -65,8 +67,8 @@
 
 extern int jfsloglevel;
 
-/* dump memory contents */
 extern void dump_mem(char *label, void *data, int length);
+extern int jfs_txanchor_read(char *, char **, off_t, int, int *, void *);
 
 /* information message: e.g., configuration, major event */
 #define jfs_info(fmt, arg...) do {			\
@@ -110,6 +112,11 @@
  *	----------
  */
 #ifdef	CONFIG_JFS_STATISTICS
+extern int jfs_lmstats_read(char *, char **, off_t, int, int *, void *);
+extern int jfs_txstats_read(char *, char **, off_t, int, int *, void *);
+extern int jfs_mpstat_read(char *, char **, off_t, int, int *, void *);
+extern int jfs_xtstat_read(char *, char **, off_t, int, int *, void *);
+
 #define	INCREMENT(x)		((x)++)
 #define	DECREMENT(x)		((x)--)
 #define	HIGHWATERMARK(x,y)	((x) = max((x), (y)))
diff --git a/fs/jfs/jfs_dmap.c b/fs/jfs/jfs_dmap.c
index 69007fd..cced2fe 100644
--- a/fs/jfs/jfs_dmap.c
+++ b/fs/jfs/jfs_dmap.c
@@ -272,7 +272,6 @@
 int dbUnmount(struct inode *ipbmap, int mounterror)
 {
 	struct bmap *bmp = JFS_SBI(ipbmap->i_sb)->bmap;
-	int i;
 
 	if (!(mounterror || isReadOnly(ipbmap)))
 		dbSync(ipbmap);
@@ -282,14 +281,6 @@
 	 */
 	truncate_inode_pages(ipbmap->i_mapping, 0);
 
-	/*
-	 * Sanity Check
-	 */
-	for (i = 0; i < bmp->db_numag; i++)
-		if (atomic_read(&bmp->db_active[i]))
-			printk(KERN_ERR "dbUnmount: db_active[%d] = %d\n",
-			       i, atomic_read(&bmp->db_active[i]));
-
 	/* free the memory for the in-memory bmap. */
 	kfree(bmp);
 
diff --git a/fs/jfs/jfs_dtree.c b/fs/jfs/jfs_dtree.c
index ac41f72..8676aee 100644
--- a/fs/jfs/jfs_dtree.c
+++ b/fs/jfs/jfs_dtree.c
@@ -2931,6 +2931,9 @@
 	ASSERT(p->header.flag & BT_LEAF);
 
 	tlck = txLock(tid, inode, mp, tlckDTREE | tlckENTRY);
+	if (BT_IS_ROOT(mp))
+		tlck->type |= tlckBTROOT;
+
 	dtlck = (struct dt_lock *) &tlck->lock;
 
 	stbl = DT_GETSTBL(p);
diff --git a/fs/jfs/jfs_extent.c b/fs/jfs/jfs_extent.c
index 1953acb..4879603 100644
--- a/fs/jfs/jfs_extent.c
+++ b/fs/jfs/jfs_extent.c
@@ -19,6 +19,7 @@
 #include <linux/fs.h>
 #include <linux/quotaops.h>
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_superblock.h"
 #include "jfs_dmap.h"
 #include "jfs_extent.h"
@@ -33,12 +34,6 @@
 #endif
 static s64 extRoundDown(s64 nb);
 
-/*
- * external references
- */
-extern int jfs_commit_inode(struct inode *, int);
-
-
 #define DPD(a)          (printk("(a): %d\n",(a)))
 #define DPC(a)          (printk("(a): %c\n",(a)))
 #define DPL1(a)					\
diff --git a/fs/jfs/jfs_imap.c b/fs/jfs/jfs_imap.c
index 7acff2c..971af29 100644
--- a/fs/jfs/jfs_imap.c
+++ b/fs/jfs/jfs_imap.c
@@ -47,6 +47,7 @@
 #include <linux/quotaops.h>
 
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_filsys.h"
 #include "jfs_dinode.h"
 #include "jfs_dmap.h"
@@ -69,11 +70,6 @@
 #define AG_UNLOCK(imap,agno)		up(&imap->im_aglock[agno])
 
 /*
- * external references
- */
-extern struct address_space_operations jfs_aops;
-
-/*
  * forward references
  */
 static int diAllocAG(struct inomap *, int, boolean_t, struct inode *);
diff --git a/fs/jfs/jfs_inode.c b/fs/jfs/jfs_inode.c
index 84f2459..2af5efb 100644
--- a/fs/jfs/jfs_inode.c
+++ b/fs/jfs/jfs_inode.c
@@ -19,6 +19,7 @@
 #include <linux/fs.h>
 #include <linux/quotaops.h>
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_filsys.h"
 #include "jfs_imap.h"
 #include "jfs_dinode.h"
diff --git a/fs/jfs/jfs_inode.h b/fs/jfs/jfs_inode.h
index 3df91fb..b54bac5 100644
--- a/fs/jfs/jfs_inode.h
+++ b/fs/jfs/jfs_inode.h
@@ -1,5 +1,5 @@
 /*
- *   Copyright (c) International Business Machines Corp., 2000-2001
+ *   Copyright (C) International Business Machines Corp., 2000-2001
  *
  *   This program is free software;  you can redistribute it and/or modify
  *   it under the terms of the GNU General Public License as published by
@@ -19,5 +19,22 @@
 #define _H_JFS_INODE
 
 extern struct inode *ialloc(struct inode *, umode_t);
+extern int jfs_fsync(struct file *, struct dentry *, int);
+extern void jfs_read_inode(struct inode *);
+extern int jfs_commit_inode(struct inode *, int);
+extern int jfs_write_inode(struct inode*, int);
+extern void jfs_delete_inode(struct inode *);
+extern void jfs_dirty_inode(struct inode *);
+extern void jfs_truncate(struct inode *);
+extern void jfs_truncate_nolock(struct inode *, loff_t);
+extern void jfs_free_zero_link(struct inode *);
+extern struct dentry *jfs_get_parent(struct dentry *dentry);
 
+extern struct address_space_operations jfs_aops;
+extern struct inode_operations jfs_dir_inode_operations;
+extern struct file_operations jfs_dir_operations;
+extern struct inode_operations jfs_file_inode_operations;
+extern struct file_operations jfs_file_operations;
+extern struct inode_operations jfs_symlink_inode_operations;
+extern struct dentry_operations jfs_ci_dentry_operations;
 #endif				/* _H_JFS_INODE */
diff --git a/fs/jfs/jfs_logmgr.c b/fs/jfs/jfs_logmgr.c
index dfa1200..7c8387e 100644
--- a/fs/jfs/jfs_logmgr.c
+++ b/fs/jfs/jfs_logmgr.c
@@ -71,6 +71,7 @@
 #include "jfs_incore.h"
 #include "jfs_filsys.h"
 #include "jfs_metapage.h"
+#include "jfs_superblock.h"
 #include "jfs_txnmgr.h"
 #include "jfs_debug.h"
 
@@ -167,14 +168,6 @@
 static DECLARE_MUTEX(jfs_log_sem);
 
 /*
- * external references
- */
-extern void txLazyUnlock(struct tblock * tblk);
-extern int jfs_stop_threads;
-extern struct completion jfsIOwait;
-extern int jfs_tlocks_low;
-
-/*
  * forward references
  */
 static int lmWriteRecord(struct jfs_log * log, struct tblock * tblk,
@@ -1624,6 +1617,8 @@
 		}
 	}
 	assert(list_empty(&log->cqueue));
+
+#ifdef CONFIG_JFS_DEBUG
 	if (!list_empty(&log->synclist)) {
 		struct logsyncblk *lp;
 
@@ -1638,9 +1633,8 @@
 				dump_mem("orphan tblock", lp,
 					 sizeof(struct tblock));
 		}
-//		current->state = TASK_INTERRUPTIBLE;
-//		schedule();
 	}
+#endif
 	//assert(list_empty(&log->synclist));
 	clear_bit(log_FLUSH, &log->flag);
 }
diff --git a/fs/jfs/jfs_logmgr.h b/fs/jfs/jfs_logmgr.h
index 51291fb..747114c 100644
--- a/fs/jfs/jfs_logmgr.h
+++ b/fs/jfs/jfs_logmgr.h
@@ -507,6 +507,8 @@
 extern int lmLogShutdown(struct jfs_log * log);
 extern int lmLogInit(struct jfs_log * log);
 extern int lmLogFormat(struct jfs_log *log, s64 logAddress, int logSize);
+extern int lmGroupCommit(struct jfs_log *, struct tblock *);
+extern int jfsIOWait(void *);
 extern void jfs_flush_journal(struct jfs_log * log, int wait);
 extern void jfs_syncpt(struct jfs_log *log);
 
diff --git a/fs/jfs/jfs_metapage.c b/fs/jfs/jfs_metapage.c
index 41bf078..6c5485d 100644
--- a/fs/jfs/jfs_metapage.c
+++ b/fs/jfs/jfs_metapage.c
@@ -198,7 +198,7 @@
 	}
 }
 
-static inline struct metapage *alloc_metapage(int gfp_mask)
+static inline struct metapage *alloc_metapage(unsigned int gfp_mask)
 {
 	return mempool_alloc(metapage_mempool, gfp_mask);
 }
@@ -726,12 +726,12 @@
 	page_cache_release(page);
 }
 
-extern void hold_metapage(struct metapage *mp)
+void hold_metapage(struct metapage *mp)
 {
 	lock_page(mp->page);
 }
 
-extern void put_metapage(struct metapage *mp)
+void put_metapage(struct metapage *mp)
 {
 	if (mp->count || mp->nohomeok) {
 		/* Someone else will release this */
diff --git a/fs/jfs/jfs_metapage.h b/fs/jfs/jfs_metapage.h
index 991e9fb..f0b7d32 100644
--- a/fs/jfs/jfs_metapage.h
+++ b/fs/jfs/jfs_metapage.h
@@ -1,6 +1,6 @@
 /*
- *   Copyright (c) International Business Machines Corp., 2000-2002
- *   Portions Copyright (c) Christoph Hellwig, 2001-2002
+ *   Copyright (C) International Business Machines Corp., 2000-2002
+ *   Portions Copyright (C) Christoph Hellwig, 2001-2002
  *
  *   This program is free software;  you can redistribute it and/or modify
  *   it under the terms of the GNU General Public License as published by
@@ -58,6 +58,8 @@
 #define mark_metapage_dirty(mp) set_bit(META_dirty, &(mp)->flag)
 
 /* function prototypes */
+extern int metapage_init(void);
+extern void metapage_exit(void);
 extern struct metapage *__get_metapage(struct inode *inode,
 				  unsigned long lblock, unsigned int size,
 				  int absolute, unsigned long new);
diff --git a/fs/jfs/jfs_superblock.h b/fs/jfs/jfs_superblock.h
index ab0566f..fcf781b 100644
--- a/fs/jfs/jfs_superblock.h
+++ b/fs/jfs/jfs_superblock.h
@@ -109,5 +109,16 @@
 extern int readSuper(struct super_block *, struct buffer_head **);
 extern int updateSuper(struct super_block *, uint);
 extern void jfs_error(struct super_block *, const char *, ...);
+extern int jfs_mount(struct super_block *);
+extern int jfs_mount_rw(struct super_block *, int);
+extern int jfs_umount(struct super_block *);
+extern int jfs_umount_rw(struct super_block *);
+
+extern int jfs_stop_threads;
+extern struct completion jfsIOwait;
+extern wait_queue_head_t jfs_IO_thread_wait;
+extern wait_queue_head_t jfs_commit_thread_wait;
+extern wait_queue_head_t jfs_sync_thread_wait;
+extern int jfs_extendfs(struct super_block *, s64, int);
 
 #endif /*_H_JFS_SUPERBLOCK */
diff --git a/fs/jfs/jfs_txnmgr.c b/fs/jfs/jfs_txnmgr.c
index e93d01a..8cbaaff 100644
--- a/fs/jfs/jfs_txnmgr.c
+++ b/fs/jfs/jfs_txnmgr.c
@@ -42,7 +42,6 @@
  * hold on to mp+lock thru update of maps
  */
 
-
 #include <linux/fs.h>
 #include <linux/vmalloc.h>
 #include <linux/smp_lock.h>
@@ -51,6 +50,7 @@
 #include <linux/module.h>
 #include <linux/moduleparam.h>
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_filsys.h"
 #include "jfs_metapage.h"
 #include "jfs_dinode.h"
@@ -109,7 +109,6 @@
 static int TxLockVHWM;		/* Very High water mark */
 struct tlock *TxLock;           /* transaction lock table */
 
-
 /*
  *      transaction management lock
  */
@@ -149,7 +148,6 @@
 
 #define TXN_WAKEUP(event) wake_up_all(event)
 
-
 /*
  *      statistics
  */
@@ -161,16 +159,6 @@
 	int waitlock;		/* 4: # of tlock wait */
 } stattx;
 
-
-/*
- * external references
- */
-extern int lmGroupCommit(struct jfs_log *, struct tblock *);
-extern int jfs_commit_inode(struct inode *, int);
-extern int jfs_stop_threads;
-
-extern struct completion jfsIOwait;
-
 /*
  * forward references
  */
@@ -358,7 +346,6 @@
 	TxBlock = NULL;
 }
 
-
 /*
  * NAME:        txBegin()
  *
@@ -460,7 +447,6 @@
 	return t;
 }
 
-
 /*
  * NAME:        txBeginAnon()
  *
@@ -503,7 +489,6 @@
 	TXN_UNLOCK();
 }
 
-
 /*
  *      txEnd()
  *
@@ -592,7 +577,6 @@
 	TXN_WAKEUP(&TxAnchor.freewait);
 }
 
-
 /*
  *      txLock()
  *
@@ -868,7 +852,6 @@
 	return NULL;
 }
 
-
 /*
  * NAME:        txRelease()
  *
@@ -908,7 +891,6 @@
 	TXN_UNLOCK();
 }
 
-
 /*
  * NAME:        txUnlock()
  *
@@ -996,7 +978,6 @@
 	}
 }
 
-
 /*
  *      txMaplock()
  *
@@ -1069,7 +1050,6 @@
 	return tlck;
 }
 
-
 /*
  *      txLinelock()
  *
@@ -1103,8 +1083,6 @@
 	return linelock;
 }
 
-
-
 /*
  *              transaction commit management
  *              -----------------------------
@@ -1373,7 +1351,6 @@
 	return rc;
 }
 
-
 /*
  * NAME:        txLog()
  *
@@ -1437,7 +1414,6 @@
 	return rc;
 }
 
-
 /*
  *      diLog()
  *
@@ -1465,7 +1441,6 @@
 	if (tlck->type & tlckENTRY) {
 		/* log after-image for logredo(): */
 		lrd->type = cpu_to_le16(LOG_REDOPAGE);
-//              *pxd = mp->cm_pxd;
 		PXDaddress(pxd, mp->index);
 		PXDlength(pxd,
 			  mp->logical_size >> tblk->sb->s_blocksize_bits);
@@ -1552,7 +1527,6 @@
 	return rc;
 }
 
-
 /*
  *      dataLog()
  *
@@ -1599,7 +1573,6 @@
 	return 0;
 }
 
-
 /*
  *      dtLog()
  *
@@ -1639,7 +1612,6 @@
 			lrd->log.redopage.type |= cpu_to_le16(LOG_EXTEND);
 		else
 			lrd->log.redopage.type |= cpu_to_le16(LOG_NEW);
-//              *pxd = mp->cm_pxd;
 		PXDaddress(pxd, mp->index);
 		PXDlength(pxd,
 			  mp->logical_size >> tblk->sb->s_blocksize_bits);
@@ -1704,7 +1676,6 @@
 	return;
 }
 
-
 /*
  *      xtLog()
  *
@@ -1760,7 +1731,6 @@
 		 * applying the after-image to the meta-data page.
 		 */
 		lrd->type = cpu_to_le16(LOG_REDOPAGE);
-//              *page_pxd = mp->cm_pxd;
 		PXDaddress(page_pxd, mp->index);
 		PXDlength(page_pxd,
 			  mp->logical_size >> tblk->sb->s_blocksize_bits);
@@ -2093,7 +2063,6 @@
 	return;
 }
 
-
 /*
  *      mapLog()
  *
@@ -2180,7 +2149,6 @@
 	}
 }
 
-
 /*
  *      txEA()
  *
@@ -2233,7 +2201,6 @@
 	}
 }
 
-
 /*
  *      txForce()
  *
@@ -2300,7 +2267,6 @@
 	}
 }
 
-
 /*
  *      txUpdateMap()
  *
@@ -2437,7 +2403,6 @@
 	}
 }
 
-
 /*
  *      txAllocPMap()
  *
@@ -2509,7 +2474,6 @@
 	}
 }
 
-
 /*
  *      txFreeMap()
  *
@@ -2611,7 +2575,6 @@
 	}
 }
 
-
 /*
  *      txFreelock()
  *
@@ -2652,7 +2615,6 @@
 	TXN_UNLOCK();
 }
 
-
 /*
  *      txAbort()
  *
diff --git a/fs/jfs/jfs_txnmgr.h b/fs/jfs/jfs_txnmgr.h
index b71b82c..59ad0f6 100644
--- a/fs/jfs/jfs_txnmgr.h
+++ b/fs/jfs/jfs_txnmgr.h
@@ -285,34 +285,26 @@
 /*
  * external declarations
  */
-extern struct tlock *txLock(tid_t tid, struct inode *ip, struct metapage *mp,
-			    int flag);
+extern int jfs_tlocks_low;
 
-extern struct tlock *txMaplock(tid_t tid, struct inode *ip, int flag);
-
-extern int txCommit(tid_t tid, int nip, struct inode **iplist, int flag);
-
-extern tid_t txBegin(struct super_block *sb, int flag);
-
-extern void txBeginAnon(struct super_block *sb);
-
-extern void txEnd(tid_t tid);
-
-extern void txAbort(tid_t tid, int dirty);
-
-extern struct linelock *txLinelock(struct linelock * tlock);
-
-extern void txFreeMap(struct inode *ip, struct maplock * maplock,
-		      struct tblock * tblk, int maptype);
-
-extern void txEA(tid_t tid, struct inode *ip, dxd_t * oldea, dxd_t * newea);
-
-extern void txFreelock(struct inode *ip);
-
-extern int lmLog(struct jfs_log * log, struct tblock * tblk, struct lrd * lrd,
-		 struct tlock * tlck);
-
-extern void txQuiesce(struct super_block *sb);
-
-extern void txResume(struct super_block *sb);
+extern int txInit(void);
+extern void txExit(void);
+extern struct tlock *txLock(tid_t, struct inode *, struct metapage *, int);
+extern struct tlock *txMaplock(tid_t, struct inode *, int);
+extern int txCommit(tid_t, int, struct inode **, int);
+extern tid_t txBegin(struct super_block *, int);
+extern void txBeginAnon(struct super_block *);
+extern void txEnd(tid_t);
+extern void txAbort(tid_t, int);
+extern struct linelock *txLinelock(struct linelock *);
+extern void txFreeMap(struct inode *, struct maplock *, struct tblock *, int);
+extern void txEA(tid_t, struct inode *, dxd_t *, dxd_t *);
+extern void txFreelock(struct inode *);
+extern int lmLog(struct jfs_log *, struct tblock *, struct lrd *,
+		 struct tlock *);
+extern void txQuiesce(struct super_block *);
+extern void txResume(struct super_block *);
+extern void txLazyUnlock(struct tblock *);
+extern int jfs_lazycommit(void *);
+extern int jfs_sync(void *);
 #endif				/* _H_JFS_TXNMGR */
diff --git a/fs/jfs/namei.c b/fs/jfs/namei.c
index 8413a36..1cae14e 100644
--- a/fs/jfs/namei.c
+++ b/fs/jfs/namei.c
@@ -31,20 +31,9 @@
 #include "jfs_acl.h"
 #include "jfs_debug.h"
 
-extern struct inode_operations jfs_file_inode_operations;
-extern struct inode_operations jfs_symlink_inode_operations;
-extern struct file_operations jfs_file_operations;
-extern struct address_space_operations jfs_aops;
-
-extern int jfs_fsync(struct file *, struct dentry *, int);
-extern void jfs_truncate_nolock(struct inode *, loff_t);
-extern int jfs_init_acl(struct inode *, struct inode *);
-
 /*
  * forward references
  */
-struct inode_operations jfs_dir_inode_operations;
-struct file_operations jfs_dir_operations;
 struct dentry_operations jfs_ci_dentry_operations;
 
 static s64 commitZeroLink(tid_t, struct inode *);
@@ -655,7 +644,7 @@
 
 
 /*
- * NAME:	freeZeroLink()
+ * NAME:	jfs_free_zero_link()
  *
  * FUNCTION:    for non-directory, called by iClose(),
  *		free resources of a file from cache and WORKING map 
@@ -663,15 +652,12 @@
  *		while associated with a pager object,
  *
  * PARAMETER:	ip	- pointer to inode of file.
- *
- * RETURN:	0 -ok
  */
-int freeZeroLink(struct inode *ip)
+void jfs_free_zero_link(struct inode *ip)
 {
-	int rc = 0;
 	int type;
 
-	jfs_info("freeZeroLink: ip = 0x%p", ip);
+	jfs_info("jfs_free_zero_link: ip = 0x%p", ip);
 
 	/* return if not reg or symbolic link or if size is
 	 * already ok.
@@ -684,10 +670,10 @@
 	case S_IFLNK:
 		/* if its contained in inode nothing to do */
 		if (ip->i_size < IDATASIZE)
-			return 0;
+			return;
 		break;
 	default:
-		return 0;
+		return;
 	}
 
 	/*
@@ -737,9 +723,7 @@
 	 * free xtree/data blocks from working block map;
 	 */
 	if (ip->i_size)
-		rc = xtTruncate(0, ip, 0, COMMIT_WMAP);
-
-	return rc;
+		xtTruncate(0, ip, 0, COMMIT_WMAP);
 }
 
 /*
diff --git a/fs/jfs/super.c b/fs/jfs/super.c
index 5e774ed..810a365 100644
--- a/fs/jfs/super.c
+++ b/fs/jfs/super.c
@@ -28,6 +28,7 @@
 
 #include "jfs_incore.h"
 #include "jfs_filsys.h"
+#include "jfs_inode.h"
 #include "jfs_metapage.h"
 #include "jfs_superblock.h"
 #include "jfs_dmap.h"
@@ -62,37 +63,6 @@
 MODULE_PARM_DESC(jfsloglevel, "Specify JFS loglevel (0, 1 or 2)");
 #endif
 
-/*
- * External declarations
- */
-extern int jfs_mount(struct super_block *);
-extern int jfs_mount_rw(struct super_block *, int);
-extern int jfs_umount(struct super_block *);
-extern int jfs_umount_rw(struct super_block *);
-
-extern int jfsIOWait(void *);
-extern int jfs_lazycommit(void *);
-extern int jfs_sync(void *);
-
-extern void jfs_read_inode(struct inode *inode);
-extern void jfs_dirty_inode(struct inode *inode);
-extern void jfs_delete_inode(struct inode *inode);
-extern int jfs_write_inode(struct inode *inode, int wait);
-
-extern struct dentry *jfs_get_parent(struct dentry *dentry);
-extern int jfs_extendfs(struct super_block *, s64, int);
-
-extern struct dentry_operations jfs_ci_dentry_operations;
-
-#ifdef PROC_FS_JFS		/* see jfs_debug.h */
-extern void jfs_proc_init(void);
-extern void jfs_proc_clean(void);
-#endif
-
-extern wait_queue_head_t jfs_IO_thread_wait;
-extern wait_queue_head_t jfs_commit_thread_wait;
-extern wait_queue_head_t jfs_sync_thread_wait;
-
 static void jfs_handle_error(struct super_block *sb)
 {
 	struct jfs_sb_info *sbi = JFS_SBI(sb);
@@ -593,11 +563,6 @@
 	.fs_flags	= FS_REQUIRES_DEV,
 };
 
-extern int metapage_init(void);
-extern int txInit(void);
-extern void txExit(void);
-extern void metapage_exit(void);
-
 static void init_once(void *foo, kmem_cache_t * cachep, unsigned long flags)
 {
 	struct jfs_inode_info *jfs_ip = (struct jfs_inode_info *) foo;
diff --git a/fs/jfs/symlink.c b/fs/jfs/symlink.c
index ef4c07e..287d8d6 100644
--- a/fs/jfs/symlink.c
+++ b/fs/jfs/symlink.c
@@ -1,5 +1,5 @@
 /*
- *   Copyright (c) Christoph Hellwig, 2001-2002
+ *   Copyright (C) Christoph Hellwig, 2001-2002
  *
  *   This program is free software;  you can redistribute it and/or modify
  *   it under the terms of the GNU General Public License as published by
@@ -19,6 +19,7 @@
 #include <linux/fs.h>
 #include <linux/namei.h>
 #include "jfs_incore.h"
+#include "jfs_inode.h"
 #include "jfs_xattr.h"
 
 static int jfs_follow_link(struct dentry *dentry, struct nameidata *nd)
diff --git a/fs/jfs/xattr.c b/fs/jfs/xattr.c
index 7a9ffd5..6016373 100644
--- a/fs/jfs/xattr.c
+++ b/fs/jfs/xattr.c
@@ -946,8 +946,7 @@
       out:
 	up_write(&JFS_IP(inode)->xattr_sem);
 
-	if (os2name)
-		kfree(os2name);
+	kfree(os2name);
 
 	return rc;
 }
@@ -1042,8 +1041,7 @@
       out:
 	up_read(&JFS_IP(inode)->xattr_sem);
 
-	if (os2name)
-		kfree(os2name);
+	kfree(os2name);
 
 	return size;
 }
diff --git a/fs/proc/proc_misc.c b/fs/proc/proc_misc.c
index a60a3b3..63a9fbf 100644
--- a/fs/proc/proc_misc.c
+++ b/fs/proc/proc_misc.c
@@ -219,6 +219,19 @@
 	.release	= seq_release,
 };
 
+extern struct seq_operations zoneinfo_op;
+static int zoneinfo_open(struct inode *inode, struct file *file)
+{
+	return seq_open(file, &zoneinfo_op);
+}
+
+static struct file_operations proc_zoneinfo_file_operations = {
+	.open		= zoneinfo_open,
+	.read		= seq_read,
+	.llseek		= seq_lseek,
+	.release	= seq_release,
+};
+
 static int version_read_proc(char *page, char **start, off_t off,
 				 int count, int *eof, void *data)
 {
@@ -589,6 +602,7 @@
 	create_seq_entry("slabinfo",S_IWUSR|S_IRUGO,&proc_slabinfo_operations);
 	create_seq_entry("buddyinfo",S_IRUGO, &fragmentation_file_operations);
 	create_seq_entry("vmstat",S_IRUGO, &proc_vmstat_file_operations);
+	create_seq_entry("zoneinfo",S_IRUGO, &proc_zoneinfo_file_operations);
 	create_seq_entry("diskstats", 0, &proc_diskstats_operations);
 #ifdef CONFIG_MODULES
 	create_seq_entry("modules", 0, &proc_modules_operations);
diff --git a/fs/super.c b/fs/super.c
index 3a1b8ca..573bcc8 100644
--- a/fs/super.c
+++ b/fs/super.c
@@ -835,6 +835,7 @@
 	mnt->mnt_parent = mnt;
 	mnt->mnt_namespace = current->namespace;
 	up_write(&sb->s_umount);
+	free_secdata(secdata);
 	put_filesystem(type);
 	return mnt;
 out_sb:
diff --git a/fs/xfs/linux-2.6/xfs_buf.c b/fs/xfs/linux-2.6/xfs_buf.c
index 997963e..c60e694 100644
--- a/fs/xfs/linux-2.6/xfs_buf.c
+++ b/fs/xfs/linux-2.6/xfs_buf.c
@@ -61,12 +61,13 @@
  * File wide globals
  */
 
-STATIC kmem_cache_t *pagebuf_cache;
+STATIC kmem_cache_t *pagebuf_zone;
 STATIC kmem_shaker_t pagebuf_shake;
-STATIC int pagebuf_daemon_wakeup(int, unsigned int);
+STATIC int xfsbufd_wakeup(int, unsigned int);
 STATIC void pagebuf_delwri_queue(xfs_buf_t *, int);
-STATIC struct workqueue_struct *pagebuf_logio_workqueue;
-STATIC struct workqueue_struct *pagebuf_dataio_workqueue;
+
+STATIC struct workqueue_struct *xfslogd_workqueue;
+STATIC struct workqueue_struct *xfsdatad_workqueue;
 
 /*
  * Pagebuf debugging
@@ -123,9 +124,9 @@
 
 
 #define pagebuf_allocate(flags) \
-	kmem_zone_alloc(pagebuf_cache, pb_to_km(flags))
+	kmem_zone_alloc(pagebuf_zone, pb_to_km(flags))
 #define pagebuf_deallocate(pb) \
-	kmem_zone_free(pagebuf_cache, (pb));
+	kmem_zone_free(pagebuf_zone, (pb));
 
 /*
  * Page Region interfaces.
@@ -425,7 +426,7 @@
 					__FUNCTION__, gfp_mask);
 
 			XFS_STATS_INC(pb_page_retries);
-			pagebuf_daemon_wakeup(0, gfp_mask);
+			xfsbufd_wakeup(0, gfp_mask);
 			blk_congestion_wait(WRITE, HZ/50);
 			goto retry;
 		}
@@ -1136,8 +1137,8 @@
 	if ((pb->pb_iodone) || (pb->pb_flags & PBF_ASYNC)) {
 		if (schedule) {
 			INIT_WORK(&pb->pb_iodone_work, pagebuf_iodone_work, pb);
-			queue_work(dataio ? pagebuf_dataio_workqueue :
-				pagebuf_logio_workqueue, &pb->pb_iodone_work);
+			queue_work(dataio ? xfsdatad_workqueue :
+				xfslogd_workqueue, &pb->pb_iodone_work);
 		} else {
 			pagebuf_iodone_work(pb);
 		}
@@ -1562,16 +1563,6 @@
 	kmem_free(btp, sizeof(*btp));
 }
 
-void
-xfs_incore_relse(
-	xfs_buftarg_t		*btp,
-	int			delwri_only,
-	int			wait)
-{
-	invalidate_bdev(btp->pbr_bdev, 1);
-	truncate_inode_pages(btp->pbr_mapping, 0LL);
-}
-
 STATIC int
 xfs_setsize_buftarg_flags(
 	xfs_buftarg_t		*btp,
@@ -1742,27 +1733,27 @@
 }
 
 /* Defines for pagebuf daemon */
-STATIC DECLARE_COMPLETION(pagebuf_daemon_done);
-STATIC struct task_struct *pagebuf_daemon_task;
-STATIC int pagebuf_daemon_active;
-STATIC int force_flush;
-STATIC int force_sleep;
+STATIC DECLARE_COMPLETION(xfsbufd_done);
+STATIC struct task_struct *xfsbufd_task;
+STATIC int xfsbufd_active;
+STATIC int xfsbufd_force_flush;
+STATIC int xfsbufd_force_sleep;
 
 STATIC int
-pagebuf_daemon_wakeup(
+xfsbufd_wakeup(
 	int			priority,
 	unsigned int		mask)
 {
-	if (force_sleep)
+	if (xfsbufd_force_sleep)
 		return 0;
-	force_flush = 1;
+	xfsbufd_force_flush = 1;
 	barrier();
-	wake_up_process(pagebuf_daemon_task);
+	wake_up_process(xfsbufd_task);
 	return 0;
 }
 
 STATIC int
-pagebuf_daemon(
+xfsbufd(
 	void			*data)
 {
 	struct list_head	tmp;
@@ -1774,17 +1765,17 @@
 	daemonize("xfsbufd");
 	current->flags |= PF_MEMALLOC;
 
-	pagebuf_daemon_task = current;
-	pagebuf_daemon_active = 1;
+	xfsbufd_task = current;
+	xfsbufd_active = 1;
 	barrier();
 
 	INIT_LIST_HEAD(&tmp);
 	do {
 		if (unlikely(current->flags & PF_FREEZE)) {
-			force_sleep = 1;
+			xfsbufd_force_sleep = 1;
 			refrigerator(PF_FREEZE);
 		} else {
-			force_sleep = 0;
+			xfsbufd_force_sleep = 0;
 		}
 
 		set_current_state(TASK_INTERRUPTIBLE);
@@ -1797,7 +1788,7 @@
 			ASSERT(pb->pb_flags & PBF_DELWRI);
 
 			if (!pagebuf_ispin(pb) && !pagebuf_cond_lock(pb)) {
-				if (!force_flush &&
+				if (!xfsbufd_force_flush &&
 				    time_before(jiffies,
 						pb->pb_queuetime + age)) {
 					pagebuf_unlock(pb);
@@ -1824,10 +1815,10 @@
 		if (as_list_len > 0)
 			purge_addresses();
 
-		force_flush = 0;
-	} while (pagebuf_daemon_active);
+		xfsbufd_force_flush = 0;
+	} while (xfsbufd_active);
 
-	complete_and_exit(&pagebuf_daemon_done, 0);
+	complete_and_exit(&xfsbufd_done, 0);
 }
 
 /*
@@ -1844,8 +1835,8 @@
 	xfs_buf_t		*pb, *n;
 	int			pincount = 0;
 
-	pagebuf_runall_queues(pagebuf_dataio_workqueue);
-	pagebuf_runall_queues(pagebuf_logio_workqueue);
+	pagebuf_runall_queues(xfsdatad_workqueue);
+	pagebuf_runall_queues(xfslogd_workqueue);
 
 	INIT_LIST_HEAD(&tmp);
 	spin_lock(&pbd_delwrite_lock);
@@ -1898,43 +1889,43 @@
 }
 
 STATIC int
-pagebuf_daemon_start(void)
+xfs_buf_daemons_start(void)
 {
-	int		rval;
+	int		error = -ENOMEM;
 
-	pagebuf_logio_workqueue = create_workqueue("xfslogd");
-	if (!pagebuf_logio_workqueue)
-		return -ENOMEM;
+	xfslogd_workqueue = create_workqueue("xfslogd");
+	if (!xfslogd_workqueue)
+		goto out;
 
-	pagebuf_dataio_workqueue = create_workqueue("xfsdatad");
-	if (!pagebuf_dataio_workqueue) {
-		destroy_workqueue(pagebuf_logio_workqueue);
-		return -ENOMEM;
-	}
+	xfsdatad_workqueue = create_workqueue("xfsdatad");
+	if (!xfsdatad_workqueue)
+		goto out_destroy_xfslogd_workqueue;
 
-	rval = kernel_thread(pagebuf_daemon, NULL, CLONE_FS|CLONE_FILES);
-	if (rval < 0) {
-		destroy_workqueue(pagebuf_logio_workqueue);
-		destroy_workqueue(pagebuf_dataio_workqueue);
-	}
+	error = kernel_thread(xfsbufd, NULL, CLONE_FS|CLONE_FILES);
+	if (error < 0)
+		goto out_destroy_xfsdatad_workqueue;
+	return 0;
 
-	return rval;
+ out_destroy_xfsdatad_workqueue:
+	destroy_workqueue(xfsdatad_workqueue);
+ out_destroy_xfslogd_workqueue:
+	destroy_workqueue(xfslogd_workqueue);
+ out:
+	return error;
 }
 
 /*
- * pagebuf_daemon_stop
- *
  * Note: do not mark as __exit, it is called from pagebuf_terminate.
  */
 STATIC void
-pagebuf_daemon_stop(void)
+xfs_buf_daemons_stop(void)
 {
-	pagebuf_daemon_active = 0;
+	xfsbufd_active = 0;
 	barrier();
-	wait_for_completion(&pagebuf_daemon_done);
+	wait_for_completion(&xfsbufd_done);
 
-	destroy_workqueue(pagebuf_logio_workqueue);
-	destroy_workqueue(pagebuf_dataio_workqueue);
+	destroy_workqueue(xfslogd_workqueue);
+	destroy_workqueue(xfsdatad_workqueue);
 }
 
 /*
@@ -1944,27 +1935,37 @@
 int __init
 pagebuf_init(void)
 {
-	pagebuf_cache = kmem_cache_create("xfs_buf_t", sizeof(xfs_buf_t), 0,
-			SLAB_HWCACHE_ALIGN, NULL, NULL);
-	if (pagebuf_cache == NULL) {
-		printk("XFS: couldn't init xfs_buf_t cache\n");
-		pagebuf_terminate();
-		return -ENOMEM;
-	}
+	int		error = -ENOMEM;
+
+	pagebuf_zone = kmem_zone_init(sizeof(xfs_buf_t), "xfs_buf");
+	if (!pagebuf_zone)
+		goto out;
 
 #ifdef PAGEBUF_TRACE
 	pagebuf_trace_buf = ktrace_alloc(PAGEBUF_TRACE_SIZE, KM_SLEEP);
 #endif
 
-	pagebuf_daemon_start();
+	error = xfs_buf_daemons_start();
+	if (error)
+		goto out_free_buf_zone;
 
-	pagebuf_shake = kmem_shake_register(pagebuf_daemon_wakeup);
-	if (pagebuf_shake == NULL) {
-		pagebuf_terminate();
-		return -ENOMEM;
+	pagebuf_shake = kmem_shake_register(xfsbufd_wakeup);
+	if (!pagebuf_shake) {
+		error = -ENOMEM;
+		goto out_stop_daemons;
 	}
 
 	return 0;
+
+ out_stop_daemons:
+	xfs_buf_daemons_stop();
+ out_free_buf_zone:
+#ifdef PAGEBUF_TRACE
+	ktrace_free(pagebuf_trace_buf);
+#endif
+	kmem_zone_destroy(pagebuf_zone);
+ out:
+	return error;
 }
 
 
@@ -1976,12 +1977,12 @@
 void
 pagebuf_terminate(void)
 {
-	pagebuf_daemon_stop();
+	xfs_buf_daemons_stop();
 
 #ifdef PAGEBUF_TRACE
 	ktrace_free(pagebuf_trace_buf);
 #endif
 
-	kmem_zone_destroy(pagebuf_cache);
+	kmem_zone_destroy(pagebuf_zone);
 	kmem_shake_deregister(pagebuf_shake);
 }
diff --git a/fs/xfs/linux-2.6/xfs_buf.h b/fs/xfs/linux-2.6/xfs_buf.h
index 74deed8..3f8f69a 100644
--- a/fs/xfs/linux-2.6/xfs_buf.h
+++ b/fs/xfs/linux-2.6/xfs_buf.h
@@ -576,7 +576,6 @@
 extern void xfs_free_buftarg(xfs_buftarg_t *, int);
 extern void xfs_wait_buftarg(xfs_buftarg_t *);
 extern int xfs_setsize_buftarg(xfs_buftarg_t *, unsigned int, unsigned int);
-extern void xfs_incore_relse(xfs_buftarg_t *, int, int);
 extern int xfs_flush_buftarg(xfs_buftarg_t *, int);
 
 #define xfs_getsize_buftarg(buftarg) \
diff --git a/fs/xfs/linux-2.6/xfs_file.c b/fs/xfs/linux-2.6/xfs_file.c
index 24fa3b1..f1ce432 100644
--- a/fs/xfs/linux-2.6/xfs_file.c
+++ b/fs/xfs/linux-2.6/xfs_file.c
@@ -57,7 +57,9 @@
 #include <linux/smp_lock.h>
 
 static struct vm_operations_struct linvfs_file_vm_ops;
-
+#ifdef CONFIG_XFS_DMAPI
+static struct vm_operations_struct linvfs_dmapi_file_vm_ops;
+#endif
 
 STATIC inline ssize_t
 __linvfs_read(
@@ -388,6 +390,14 @@
 	return -error;
 }
 
+#ifdef CONFIG_XFS_DMAPI
+STATIC void
+linvfs_mmap_close(
+	struct vm_area_struct	*vma)
+{
+	xfs_dm_mm_put(vma);
+}
+#endif /* CONFIG_XFS_DMAPI */
 
 STATIC int
 linvfs_file_mmap(
@@ -399,16 +409,19 @@
 	vattr_t		va = { .va_mask = XFS_AT_UPDATIME };
 	int		error;
 
+	vma->vm_ops = &linvfs_file_vm_ops;
+
 	if (vp->v_vfsp->vfs_flag & VFS_DMI) {
 		xfs_mount_t	*mp = XFS_VFSTOM(vp->v_vfsp);
 
 		error = -XFS_SEND_MMAP(mp, vma, 0);
 		if (error)
 			return error;
+#ifdef CONFIG_XFS_DMAPI
+		vma->vm_ops = &linvfs_dmapi_file_vm_ops;
+#endif
 	}
 
-	vma->vm_ops = &linvfs_file_vm_ops;
-
 	VOP_SETATTR(vp, &va, XFS_AT_UPDATIME, NULL, error);
 	if (!error)
 		vn_revalidate(vp);	/* update Linux inode flags */
@@ -609,7 +622,15 @@
 static struct vm_operations_struct linvfs_file_vm_ops = {
 	.nopage		= filemap_nopage,
 	.populate	= filemap_populate,
+};
+
+#ifdef CONFIG_XFS_DMAPI
+static struct vm_operations_struct linvfs_dmapi_file_vm_ops = {
+	.close		= linvfs_mmap_close,
+	.nopage		= filemap_nopage,
+	.populate	= filemap_populate,
 #ifdef HAVE_VMOP_MPROTECT
 	.mprotect	= linvfs_mprotect,
 #endif
 };
+#endif /* CONFIG_XFS_DMAPI */
diff --git a/fs/xfs/linux-2.6/xfs_ioctl.c b/fs/xfs/linux-2.6/xfs_ioctl.c
index 69809ee..05a447e 100644
--- a/fs/xfs/linux-2.6/xfs_ioctl.c
+++ b/fs/xfs/linux-2.6/xfs_ioctl.c
@@ -1174,7 +1174,8 @@
 
 	switch (cmd) {
 	case XFS_IOC_FSGETXATTR: {
-		va.va_mask = XFS_AT_XFLAGS|XFS_AT_EXTSIZE|XFS_AT_NEXTENTS;
+		va.va_mask = XFS_AT_XFLAGS | XFS_AT_EXTSIZE | \
+			     XFS_AT_NEXTENTS | XFS_AT_PROJID;
 		VOP_GETATTR(vp, &va, 0, NULL, error);
 		if (error)
 			return -error;
@@ -1182,6 +1183,7 @@
 		fa.fsx_xflags	= va.va_xflags;
 		fa.fsx_extsize	= va.va_extsize;
 		fa.fsx_nextents = va.va_nextents;
+		fa.fsx_projid	= va.va_projid;
 
 		if (copy_to_user(arg, &fa, sizeof(fa)))
 			return -XFS_ERROR(EFAULT);
@@ -1196,9 +1198,10 @@
 		if (filp->f_flags & (O_NDELAY|O_NONBLOCK))
 			attr_flags |= ATTR_NONBLOCK;
 
-		va.va_mask = XFS_AT_XFLAGS | XFS_AT_EXTSIZE;
+		va.va_mask = XFS_AT_XFLAGS | XFS_AT_EXTSIZE | XFS_AT_PROJID;
 		va.va_xflags  = fa.fsx_xflags;
 		va.va_extsize = fa.fsx_extsize;
+		va.va_projid  = fa.fsx_projid;
 
 		VOP_SETATTR(vp, &va, attr_flags, NULL, error);
 		if (!error)
@@ -1207,7 +1210,8 @@
 	}
 
 	case XFS_IOC_FSGETXATTRA: {
-		va.va_mask = XFS_AT_XFLAGS|XFS_AT_EXTSIZE|XFS_AT_ANEXTENTS;
+		va.va_mask = XFS_AT_XFLAGS | XFS_AT_EXTSIZE | \
+			     XFS_AT_ANEXTENTS | XFS_AT_PROJID;
 		VOP_GETATTR(vp, &va, 0, NULL, error);
 		if (error)
 			return -error;
@@ -1215,6 +1219,7 @@
 		fa.fsx_xflags	= va.va_xflags;
 		fa.fsx_extsize	= va.va_extsize;
 		fa.fsx_nextents = va.va_anextents;
+		fa.fsx_projid	= va.va_projid;
 
 		if (copy_to_user(arg, &fa, sizeof(fa)))
 			return -XFS_ERROR(EFAULT);
diff --git a/fs/xfs/linux-2.6/xfs_linux.h b/fs/xfs/linux-2.6/xfs_linux.h
index 71bb410..42dc5e4 100644
--- a/fs/xfs/linux-2.6/xfs_linux.h
+++ b/fs/xfs/linux-2.6/xfs_linux.h
@@ -145,10 +145,10 @@
 #define xfs_inherit_nosymlinks	xfs_params.inherit_nosym.val
 #define xfs_rotorstep		xfs_params.rotorstep.val
 
-#ifndef __smp_processor_id
-#define __smp_processor_id()	smp_processor_id()
+#ifndef raw_smp_processor_id
+#define raw_smp_processor_id()	smp_processor_id()
 #endif
-#define current_cpu()		__smp_processor_id()
+#define current_cpu()		raw_smp_processor_id()
 #define current_pid()		(current->pid)
 #define current_fsuid(cred)	(current->fsuid)
 #define current_fsgid(cred)	(current->fsgid)
@@ -230,8 +230,10 @@
  * field (see the QCMD macro in quota.h).  These macros help keep the
  * code portable - they are not visible from the syscall interface.
  */
-#define Q_XSETGQLIM	XQM_CMD(0x8)	/* set groups disk limits */
-#define Q_XGETGQUOTA	XQM_CMD(0x9)	/* get groups disk limits */
+#define Q_XSETGQLIM	XQM_CMD(8)	/* set groups disk limits */
+#define Q_XGETGQUOTA	XQM_CMD(9)	/* get groups disk limits */
+#define Q_XSETPQLIM	XQM_CMD(10)	/* set projects disk limits */
+#define Q_XGETPQUOTA	XQM_CMD(11)	/* get projects disk limits */
 
 /* IRIX uses a dynamic sizing algorithm (ndquot = 200 + numprocs*2) */
 /* we may well need to fine-tune this if it ever becomes an issue.  */
diff --git a/fs/xfs/linux-2.6/xfs_lrw.c b/fs/xfs/linux-2.6/xfs_lrw.c
index aa9daae..acab58c 100644
--- a/fs/xfs/linux-2.6/xfs_lrw.c
+++ b/fs/xfs/linux-2.6/xfs_lrw.c
@@ -209,30 +209,6 @@
 	return (-status);
 }
 
-/*
- * xfs_inval_cached_pages
- * 
- * This routine is responsible for keeping direct I/O and buffered I/O
- * somewhat coherent.  From here we make sure that we're at least
- * temporarily holding the inode I/O lock exclusively and then call
- * the page cache to flush and invalidate any cached pages.  If there
- * are no cached pages this routine will be very quick.
- */
-void
-xfs_inval_cached_pages(
-	vnode_t		*vp,
-	xfs_iocore_t	*io,
-	xfs_off_t	offset,
-	int		write,
-	int		relock)
-{
-	if (VN_CACHED(vp)) {
-		xfs_inval_cached_trace(io, offset, -1, ctooff(offtoct(offset)), -1);
-		VOP_FLUSHINVAL_PAGES(vp, ctooff(offtoct(offset)), -1, FI_REMAPF_LOCKED);
-	}
-
-}
-
 ssize_t			/* bytes read, or (-)  error */
 xfs_read(
 	bhv_desc_t		*bdp,
@@ -304,10 +280,11 @@
 	if (DM_EVENT_ENABLED(vp->v_vfsp, ip, DM_EVENT_READ) &&
 	    !(ioflags & IO_INVIS)) {
 		vrwlock_t locktype = VRWLOCK_READ;
+		int dmflags = FILP_DELAY_FLAG(file) | DM_SEM_FLAG_RD(ioflags);
 
 		ret = -XFS_SEND_DATA(mp, DM_EVENT_READ,
 					BHV_TO_VNODE(bdp), *offset, size,
-					FILP_DELAY_FLAG(file), &locktype);
+					dmflags, &locktype);
 		if (ret) {
 			xfs_iunlock(ip, XFS_IOLOCK_SHARED);
 			goto unlock_isem;
@@ -867,11 +844,15 @@
 	    !(ioflags & IO_INVIS)) {
 
 		xfs_rwunlock(bdp, locktype);
+		if (need_isem)
+			up(&inode->i_sem);
 		error = XFS_SEND_NAMESP(xip->i_mount, DM_EVENT_NOSPACE, vp,
 				DM_RIGHT_NULL, vp, DM_RIGHT_NULL, NULL, NULL,
 				0, 0, 0); /* Delay flag intentionally  unused */
 		if (error)
-			goto out_unlock_isem;
+			goto out_nounlocks;
+		if (need_isem)
+			down(&inode->i_sem);
 		xfs_rwlock(bdp, locktype);
 		pos = xip->i_d.di_size;
 		ret = 0;
@@ -986,6 +967,7 @@
  out_unlock_isem:
 	if (need_isem)
 		up(&inode->i_sem);
+ out_nounlocks:
 	return -error;
 }
 
diff --git a/fs/xfs/linux-2.6/xfs_lrw.h b/fs/xfs/linux-2.6/xfs_lrw.h
index d723e35..f197a72 100644
--- a/fs/xfs/linux-2.6/xfs_lrw.h
+++ b/fs/xfs/linux-2.6/xfs_lrw.h
@@ -94,8 +94,6 @@
 
 extern int xfs_zero_eof(struct vnode *, struct xfs_iocore *, xfs_off_t,
 				xfs_fsize_t, xfs_fsize_t);
-extern void xfs_inval_cached_pages(struct vnode	*, struct xfs_iocore *,
-				xfs_off_t, int, int);
 extern ssize_t xfs_read(struct bhv_desc *, struct kiocb *,
 				const struct iovec *, unsigned int,
 				loff_t *, int, struct cred *);
diff --git a/fs/xfs/linux-2.6/xfs_super.c b/fs/xfs/linux-2.6/xfs_super.c
index 455e2b2..5fe9af3 100644
--- a/fs/xfs/linux-2.6/xfs_super.c
+++ b/fs/xfs/linux-2.6/xfs_super.c
@@ -590,8 +590,10 @@
 	int		error;
 	int		flags = SYNC_FSDATA;
 
-	if (wait)
-		flags |= SYNC_WAIT;
+	if (unlikely(sb->s_frozen == SB_FREEZE_WRITE))
+		flags = SYNC_QUIESCE;
+	else
+		flags = SYNC_FSDATA | (wait ? SYNC_WAIT : 0);
 
 	VFS_SYNC(vfsp, flags, NULL, error);
 	sb->s_dirt = 0;
@@ -701,7 +703,8 @@
 	struct vfs		*vfsp = LINVFS_GET_VFS(sb);
 	int			error, getmode;
 
-	getmode = (type == GRPQUOTA) ? Q_XGETGQUOTA : Q_XGETQUOTA;
+	getmode = (type == USRQUOTA) ? Q_XGETQUOTA :
+		 ((type == GRPQUOTA) ? Q_XGETGQUOTA : Q_XGETPQUOTA);
 	VFS_QUOTACTL(vfsp, getmode, id, (caddr_t)fdq, error);
 	return -error;
 }
@@ -716,7 +719,8 @@
 	struct vfs		*vfsp = LINVFS_GET_VFS(sb);
 	int			error, setmode;
 
-	setmode = (type == GRPQUOTA) ? Q_XSETGQLIM : Q_XSETQLIM;
+	setmode = (type == USRQUOTA) ? Q_XSETQLIM :
+		 ((type == GRPQUOTA) ? Q_XSETGQLIM : Q_XSETPQLIM);
 	VFS_QUOTACTL(vfsp, setmode, id, (caddr_t)fdq, error);
 	return -error;
 }
diff --git a/fs/xfs/linux-2.6/xfs_vfs.h b/fs/xfs/linux-2.6/xfs_vfs.h
index 7649399..7ee1f71 100644
--- a/fs/xfs/linux-2.6/xfs_vfs.h
+++ b/fs/xfs/linux-2.6/xfs_vfs.h
@@ -107,6 +107,7 @@
 #define SYNC_FSDATA		0x0020	/* flush fs data (e.g. superblocks) */
 #define SYNC_REFCACHE		0x0040  /* prune some of the nfs ref cache */
 #define SYNC_REMOUNT		0x0080  /* remount readonly, no dummy LRs */
+#define SYNC_QUIESCE		0x0100  /* quiesce fileystem for a snapshot */
 
 typedef int	(*vfs_mount_t)(bhv_desc_t *,
 				struct xfs_mount_args *, struct cred *);
diff --git a/fs/xfs/linux-2.6/xfs_vnode.c b/fs/xfs/linux-2.6/xfs_vnode.c
index a832d16..250cad5 100644
--- a/fs/xfs/linux-2.6/xfs_vnode.c
+++ b/fs/xfs/linux-2.6/xfs_vnode.c
@@ -411,13 +411,13 @@
 /*  0 */		(void *)(__psint_t)(vk),		\
 /*  1 */		(void *)(s),				\
 /*  2 */		(void *)(__psint_t) line,		\
-/*  3 */		(void *)(vn_count(vp)), \
+/*  3 */		(void *)(__psint_t)(vn_count(vp)),	\
 /*  4 */		(void *)(ra),				\
 /*  5 */		(void *)(__psunsigned_t)(vp)->v_flag,	\
 /*  6 */		(void *)(__psint_t)current_cpu(),	\
 /*  7 */		(void *)(__psint_t)current_pid(),	\
 /*  8 */		(void *)__return_address,		\
-/*  9 */		0, 0, 0, 0, 0, 0, 0)
+/*  9 */		NULL, NULL, NULL, NULL, NULL, NULL, NULL)
 
 /*
  * Vnode tracing code.
diff --git a/fs/xfs/linux-2.6/xfs_vnode.h b/fs/xfs/linux-2.6/xfs_vnode.h
index 00466c3..a6e57c6 100644
--- a/fs/xfs/linux-2.6/xfs_vnode.h
+++ b/fs/xfs/linux-2.6/xfs_vnode.h
@@ -426,7 +426,7 @@
 	u_long		va_extsize;	/* file extent size */
 	u_long		va_nextents;	/* number of extents in file */
 	u_long		va_anextents;	/* number of attr extents in file */
-	int		va_projid;	/* project id */
+	prid_t		va_projid;	/* project id */
 } vattr_t;
 
 /*
diff --git a/fs/xfs/quota/xfs_dquot.c b/fs/xfs/quota/xfs_dquot.c
index 740d20d..46ce1e3 100644
--- a/fs/xfs/quota/xfs_dquot.c
+++ b/fs/xfs/quota/xfs_dquot.c
@@ -101,7 +101,7 @@
  * is the d_id field. The idea is to fill in the entire q_core
  * when we read in the on disk dquot.
  */
-xfs_dquot_t *
+STATIC xfs_dquot_t *
 xfs_qm_dqinit(
 	xfs_mount_t  *mp,
 	xfs_dqid_t   id,
@@ -286,7 +286,9 @@
  * We also return 0 as the values of the timers in Q_GETQUOTA calls, when
  * enforcement's off.
  * In contrast, warnings are a little different in that they don't
- * 'automatically' get started when limits get exceeded.
+ * 'automatically' get started when limits get exceeded.  They do
+ * get reset to zero, however, when we find the count to be under
+ * the soft limit (they are only ever set non-zero via userspace).
  */
 void
 xfs_qm_adjust_dqtimers(
@@ -315,6 +317,8 @@
 				INT_GET(d->d_blk_hardlimit, ARCH_CONVERT)))) {
 			INT_SET(d->d_btimer, ARCH_CONVERT,
 				get_seconds() + XFS_QI_BTIMELIMIT(mp));
+		} else {
+			d->d_bwarns = 0;
 		}
 	} else {
 		if ((!d->d_blk_softlimit ||
@@ -336,6 +340,8 @@
 				INT_GET(d->d_ino_hardlimit, ARCH_CONVERT)))) {
 			INT_SET(d->d_itimer, ARCH_CONVERT,
 				get_seconds() + XFS_QI_ITIMELIMIT(mp));
+		} else {
+			d->d_iwarns = 0;
 		}
 	} else {
 		if ((!d->d_ino_softlimit ||
@@ -357,6 +363,8 @@
 				INT_GET(d->d_rtb_hardlimit, ARCH_CONVERT)))) {
 			INT_SET(d->d_rtbtimer, ARCH_CONVERT,
 				get_seconds() + XFS_QI_RTBTIMELIMIT(mp));
+		} else {
+			d->d_rtbwarns = 0;
 		}
 	} else {
 		if ((!d->d_rtb_softlimit ||
@@ -371,68 +379,6 @@
 }
 
 /*
- * Increment or reset warnings of a given dquot.
- */
-int
-xfs_qm_dqwarn(
-	xfs_disk_dquot_t	*d,
-	uint			flags)
-{
-	int	warned;
-
-	/*
-	 * root's limits are not real limits.
-	 */
-	if (!d->d_id)
-		return (0);
-
-	warned = 0;
-	if (INT_GET(d->d_blk_softlimit, ARCH_CONVERT) &&
-	    (INT_GET(d->d_bcount, ARCH_CONVERT) >=
-	     INT_GET(d->d_blk_softlimit, ARCH_CONVERT))) {
-		if (flags & XFS_QMOPT_DOWARN) {
-			INT_MOD(d->d_bwarns, ARCH_CONVERT, +1);
-			warned++;
-		}
-	} else {
-		if (!d->d_blk_softlimit ||
-		    (INT_GET(d->d_bcount, ARCH_CONVERT) <
-		     INT_GET(d->d_blk_softlimit, ARCH_CONVERT))) {
-			d->d_bwarns = 0;
-		}
-	}
-
-	if (INT_GET(d->d_ino_softlimit, ARCH_CONVERT) > 0 &&
-	    (INT_GET(d->d_icount, ARCH_CONVERT) >=
-	     INT_GET(d->d_ino_softlimit, ARCH_CONVERT))) {
-		if (flags & XFS_QMOPT_DOWARN) {
-			INT_MOD(d->d_iwarns, ARCH_CONVERT, +1);
-			warned++;
-		}
-	} else {
-		if (!d->d_ino_softlimit ||
-		    (INT_GET(d->d_icount, ARCH_CONVERT) <
-		     INT_GET(d->d_ino_softlimit, ARCH_CONVERT))) {
-			d->d_iwarns = 0;
-		}
-	}
-#ifdef QUOTADEBUG
-	if (INT_GET(d->d_iwarns, ARCH_CONVERT))
-		cmn_err(CE_DEBUG,
-			"--------@@Inode warnings running : %Lu >= %Lu",
-			INT_GET(d->d_icount, ARCH_CONVERT),
-			INT_GET(d->d_ino_softlimit, ARCH_CONVERT));
-	if (INT_GET(d->d_bwarns, ARCH_CONVERT))
-		cmn_err(CE_DEBUG,
-			"--------@@Blks warnings running : %Lu >= %Lu",
-			INT_GET(d->d_bcount, ARCH_CONVERT),
-			INT_GET(d->d_blk_softlimit, ARCH_CONVERT));
-#endif
-	return (warned);
-}
-
-
-/*
  * initialize a buffer full of dquots and log the whole thing
  */
 STATIC void
@@ -461,9 +407,9 @@
 	for (i = 0; i < XFS_QM_DQPERBLK(mp); i++, d++, curid++)
 		xfs_qm_dqinit_core(curid, type, d);
 	xfs_trans_dquot_buf(tp, bp,
-			    type & XFS_DQ_USER ?
-			    XFS_BLI_UDQUOT_BUF :
-			    XFS_BLI_GDQUOT_BUF);
+			    (type & XFS_DQ_USER ? XFS_BLI_UDQUOT_BUF :
+			    ((type & XFS_DQ_PROJ) ? XFS_BLI_PDQUOT_BUF :
+			     XFS_BLI_GDQUOT_BUF)));
 	xfs_trans_log_buf(tp, bp, 0, BBTOB(XFS_QI_DQCHUNKLEN(mp)) - 1);
 }
 
@@ -544,8 +490,7 @@
 	 * the entire thing.
 	 */
 	xfs_qm_init_dquot_blk(tp, mp, INT_GET(dqp->q_core.d_id, ARCH_CONVERT),
-			      dqp->dq_flags & (XFS_DQ_USER|XFS_DQ_GROUP),
-			      bp);
+			      dqp->dq_flags & XFS_DQ_ALLTYPES, bp);
 
 	if ((error = xfs_bmap_finish(&tp, &flist, firstblock, &committed))) {
 		goto error1;
@@ -675,8 +620,7 @@
 	/*
 	 * A simple sanity check in case we got a corrupted dquot...
 	 */
-	if (xfs_qm_dqcheck(ddq, id,
-			   dqp->dq_flags & (XFS_DQ_USER|XFS_DQ_GROUP),
+	if (xfs_qm_dqcheck(ddq, id, dqp->dq_flags & XFS_DQ_ALLTYPES,
 			   flags & (XFS_QMOPT_DQREPAIR|XFS_QMOPT_DOWARN),
 			   "dqtobp")) {
 		if (!(flags & XFS_QMOPT_DQREPAIR)) {
@@ -953,8 +897,8 @@
 xfs_qm_dqget(
 	xfs_mount_t	*mp,
 	xfs_inode_t	*ip,	  /* locked inode (optional) */
-	xfs_dqid_t	id,	  /* gid or uid, depending on type */
-	uint		type,	  /* UDQUOT or GDQUOT */
+	xfs_dqid_t	id,	  /* uid/projid/gid depending on type */
+	uint		type,	  /* XFS_DQ_USER/XFS_DQ_PROJ/XFS_DQ_GROUP */
 	uint		flags,	  /* DQALLOC, DQSUSER, DQREPAIR, DOWARN */
 	xfs_dquot_t	**O_dqpp) /* OUT : locked incore dquot */
 {
@@ -965,6 +909,7 @@
 
 	ASSERT(XFS_IS_QUOTA_RUNNING(mp));
 	if ((! XFS_IS_UQUOTA_ON(mp) && type == XFS_DQ_USER) ||
+	    (! XFS_IS_PQUOTA_ON(mp) && type == XFS_DQ_PROJ) ||
 	    (! XFS_IS_GQUOTA_ON(mp) && type == XFS_DQ_GROUP)) {
 		return (ESRCH);
 	}
@@ -983,7 +928,9 @@
  again:
 
 #ifdef DEBUG
-	ASSERT(type == XFS_DQ_USER || type == XFS_DQ_GROUP);
+	ASSERT(type == XFS_DQ_USER ||
+	       type == XFS_DQ_PROJ ||
+	       type == XFS_DQ_GROUP);
 	if (ip) {
 		ASSERT(XFS_ISLOCKED_INODE_EXCL(ip));
 		if (type == XFS_DQ_USER)
@@ -1306,8 +1253,8 @@
 		return (error);
 	}
 
-	if (xfs_qm_dqcheck(&dqp->q_core, INT_GET(ddqp->d_id, ARCH_CONVERT), 0, XFS_QMOPT_DOWARN,
-			   "dqflush (incore copy)")) {
+	if (xfs_qm_dqcheck(&dqp->q_core, INT_GET(ddqp->d_id, ARCH_CONVERT),
+			   0, XFS_QMOPT_DOWARN, "dqflush (incore copy)")) {
 		xfs_force_shutdown(dqp->q_mount, XFS_CORRUPT_INCORE);
 		return XFS_ERROR(EIO);
 	}
@@ -1459,7 +1406,8 @@
 {
 	if (d1 && d2) {
 		ASSERT(d1 != d2);
-		if (INT_GET(d1->q_core.d_id, ARCH_CONVERT) > INT_GET(d2->q_core.d_id, ARCH_CONVERT)) {
+		if (INT_GET(d1->q_core.d_id, ARCH_CONVERT) >
+		    INT_GET(d2->q_core.d_id, ARCH_CONVERT)) {
 			xfs_dqlock(d2);
 			xfs_dqlock(d1);
 		} else {
@@ -1582,8 +1530,7 @@
 	cmn_err(CE_DEBUG, "-----------KERNEL DQUOT----------------");
 	cmn_err(CE_DEBUG, "---- dquotID =  %d",
 		(int)INT_GET(dqp->q_core.d_id, ARCH_CONVERT));
-	cmn_err(CE_DEBUG, "---- type    =  %s",
-		XFS_QM_ISUDQ(dqp) ? "USR" : "GRP");
+	cmn_err(CE_DEBUG, "---- type    =  %s", DQFLAGTO_TYPESTR(dqp));
 	cmn_err(CE_DEBUG, "---- fs      =  0x%p", dqp->q_mount);
 	cmn_err(CE_DEBUG, "---- blkno   =  0x%x", (int) dqp->q_blkno);
 	cmn_err(CE_DEBUG, "---- boffset =  0x%x", (int) dqp->q_bufoffset);
diff --git a/fs/xfs/quota/xfs_dquot.h b/fs/xfs/quota/xfs_dquot.h
index 0c3fe31..3917510 100644
--- a/fs/xfs/quota/xfs_dquot.h
+++ b/fs/xfs/quota/xfs_dquot.h
@@ -114,25 +114,18 @@
 #define XFS_DQHOLD(dqp)		((dqp)->q_nrefs++)
 
 /*
- * Quota Accounting flags
+ * Quota Accounting/Enforcement flags
  */
-#define XFS_ALL_QUOTA_ACCT	(XFS_UQUOTA_ACCT | XFS_GQUOTA_ACCT)
-#define XFS_ALL_QUOTA_ENFD	(XFS_UQUOTA_ENFD | XFS_GQUOTA_ENFD)
-#define XFS_ALL_QUOTA_CHKD	(XFS_UQUOTA_CHKD | XFS_GQUOTA_CHKD)
-#define XFS_ALL_QUOTA_ACTV	(XFS_UQUOTA_ACTIVE | XFS_GQUOTA_ACTIVE)
-#define XFS_ALL_QUOTA_ACCT_ENFD (XFS_UQUOTA_ACCT|XFS_UQUOTA_ENFD|\
-				 XFS_GQUOTA_ACCT|XFS_GQUOTA_ENFD)
+#define XFS_ALL_QUOTA_ACCT	\
+		(XFS_UQUOTA_ACCT | XFS_GQUOTA_ACCT | XFS_PQUOTA_ACCT)
+#define XFS_ALL_QUOTA_ENFD	(XFS_UQUOTA_ENFD | XFS_OQUOTA_ENFD)
+#define XFS_ALL_QUOTA_CHKD	(XFS_UQUOTA_CHKD | XFS_OQUOTA_CHKD)
 
-#define XFS_IS_QUOTA_RUNNING(mp)  ((mp)->m_qflags & XFS_ALL_QUOTA_ACCT)
-#define XFS_IS_UQUOTA_RUNNING(mp) ((mp)->m_qflags & XFS_UQUOTA_ACCT)
-#define XFS_IS_GQUOTA_RUNNING(mp) ((mp)->m_qflags & XFS_GQUOTA_ACCT)
-
-/*
- * Quota Limit Enforcement flags
- */
+#define XFS_IS_QUOTA_RUNNING(mp)	((mp)->m_qflags & XFS_ALL_QUOTA_ACCT)
 #define XFS_IS_QUOTA_ENFORCED(mp)	((mp)->m_qflags & XFS_ALL_QUOTA_ENFD)
-#define XFS_IS_UQUOTA_ENFORCED(mp)	((mp)->m_qflags & XFS_UQUOTA_ENFD)
-#define XFS_IS_GQUOTA_ENFORCED(mp)	((mp)->m_qflags & XFS_GQUOTA_ENFD)
+#define XFS_IS_UQUOTA_RUNNING(mp)	((mp)->m_qflags & XFS_UQUOTA_ACCT)
+#define XFS_IS_PQUOTA_RUNNING(mp)	((mp)->m_qflags & XFS_PQUOTA_ACCT)
+#define XFS_IS_GQUOTA_RUNNING(mp)	((mp)->m_qflags & XFS_GQUOTA_ACCT)
 
 #ifdef DEBUG
 static inline int
@@ -167,6 +160,8 @@
 #define XFS_DQ_IS_ON_FREELIST(dqp)  ((dqp)->dq_flnext != (dqp))
 #define XFS_DQ_IS_DIRTY(dqp)	((dqp)->dq_flags & XFS_DQ_DIRTY)
 #define XFS_QM_ISUDQ(dqp)	((dqp)->dq_flags & XFS_DQ_USER)
+#define XFS_QM_ISPDQ(dqp)	((dqp)->dq_flags & XFS_DQ_PROJ)
+#define XFS_QM_ISGDQ(dqp)	((dqp)->dq_flags & XFS_DQ_GROUP)
 #define XFS_DQ_TO_QINF(dqp)	((dqp)->q_mount->m_quotainfo)
 #define XFS_DQ_TO_QIP(dqp)	(XFS_QM_ISUDQ(dqp) ? \
 				 XFS_DQ_TO_QINF(dqp)->qi_uquotaip : \
@@ -174,7 +169,7 @@
 
 #define XFS_IS_THIS_QUOTA_OFF(d) (! (XFS_QM_ISUDQ(d) ? \
 				     (XFS_IS_UQUOTA_ON((d)->q_mount)) : \
-				     (XFS_IS_GQUOTA_ON((d)->q_mount))))
+				     (XFS_IS_OQUOTA_ON((d)->q_mount))))
 
 #ifdef XFS_DQUOT_TRACE
 /*
@@ -211,7 +206,6 @@
 					xfs_disk_dquot_t *);
 extern void		xfs_qm_adjust_dqlimits(xfs_mount_t *,
 					xfs_disk_dquot_t *);
-extern int		xfs_qm_dqwarn(xfs_disk_dquot_t *, uint);
 extern int		xfs_qm_dqget(xfs_mount_t *, xfs_inode_t *,
 					xfs_dqid_t, uint, uint, xfs_dquot_t **);
 extern void		xfs_qm_dqput(xfs_dquot_t *);
diff --git a/fs/xfs/quota/xfs_dquot_item.c b/fs/xfs/quota/xfs_dquot_item.c
index a5425ee..f5271b7 100644
--- a/fs/xfs/quota/xfs_dquot_item.c
+++ b/fs/xfs/quota/xfs_dquot_item.c
@@ -428,7 +428,7 @@
 /*
  * This is the ops vector for dquots
  */
-struct xfs_item_ops xfs_dquot_item_ops = {
+STATIC struct xfs_item_ops xfs_dquot_item_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_qm_dquot_logitem_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_qm_dquot_logitem_format,
@@ -646,7 +646,7 @@
 	return;
 }
 
-struct xfs_item_ops xfs_qm_qoffend_logitem_ops = {
+STATIC struct xfs_item_ops xfs_qm_qoffend_logitem_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_qm_qoff_logitem_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_qm_qoff_logitem_format,
@@ -669,7 +669,7 @@
 /*
  * This is the ops vector shared by all quotaoff-start log items.
  */
-struct xfs_item_ops xfs_qm_qoff_logitem_ops = {
+STATIC struct xfs_item_ops xfs_qm_qoff_logitem_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_qm_qoff_logitem_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_qm_qoff_logitem_format,
diff --git a/fs/xfs/quota/xfs_qm.c b/fs/xfs/quota/xfs_qm.c
index 89f2cd6..f665ca8f 100644
--- a/fs/xfs/quota/xfs_qm.c
+++ b/fs/xfs/quota/xfs_qm.c
@@ -81,12 +81,18 @@
 
 kmem_zone_t	*qm_dqzone;
 kmem_zone_t	*qm_dqtrxzone;
-kmem_shaker_t	xfs_qm_shaker;
+STATIC kmem_shaker_t	xfs_qm_shaker;
 
 STATIC void	xfs_qm_list_init(xfs_dqlist_t *, char *, int);
 STATIC void	xfs_qm_list_destroy(xfs_dqlist_t *);
 
+STATIC void	xfs_qm_freelist_init(xfs_frlist_t *);
+STATIC void	xfs_qm_freelist_destroy(xfs_frlist_t *);
+STATIC int	xfs_qm_mplist_nowait(xfs_mount_t *);
+STATIC int	xfs_qm_dqhashlock_nowait(xfs_dquot_t *);
+
 STATIC int	xfs_qm_init_quotainos(xfs_mount_t *);
+STATIC int	xfs_qm_init_quotainfo(xfs_mount_t *);
 STATIC int	xfs_qm_shake(int, unsigned int);
 
 #ifdef DEBUG
@@ -184,7 +190,7 @@
 /*
  * Destroy the global quota manager when its reference count goes to zero.
  */
-void
+STATIC void
 xfs_qm_destroy(
 	struct xfs_qm	*xqm)
 {
@@ -304,9 +310,9 @@
 	uint		flags)
 {
 	/*
-	 * User or group quotas has to be on.
+	 * User, projects or group quotas has to be on.
 	 */
-	ASSERT(flags & (XFSMNT_UQUOTA | XFSMNT_GQUOTA));
+	ASSERT(flags & (XFSMNT_UQUOTA | XFSMNT_PQUOTA | XFSMNT_GQUOTA));
 
 	/*
 	 * Initialize the flags in the mount structure. From this point
@@ -324,7 +330,11 @@
 	if (flags & XFSMNT_GQUOTA) {
 		mp->m_qflags |= (XFS_GQUOTA_ACCT | XFS_GQUOTA_ACTIVE);
 		if (flags & XFSMNT_GQUOTAENF)
-			mp->m_qflags |= XFS_GQUOTA_ENFD;
+			mp->m_qflags |= XFS_OQUOTA_ENFD;
+	} else if (flags & XFSMNT_PQUOTA) {
+		mp->m_qflags |= (XFS_PQUOTA_ACCT | XFS_PQUOTA_ACTIVE);
+		if (flags & XFSMNT_PQUOTAENF)
+			mp->m_qflags |= XFS_OQUOTA_ENFD;
 	}
 }
 
@@ -357,11 +367,11 @@
 
 	/*
 	 * If a file system had quotas running earlier, but decided to
-	 * mount without -o quota/uquota/gquota options, revoke the
+	 * mount without -o uquota/pquota/gquota options, revoke the
 	 * quotachecked license, and bail out.
 	 */
 	if (! XFS_IS_QUOTA_ON(mp) &&
-	    (mp->m_sb.sb_qflags & (XFS_UQUOTA_ACCT|XFS_GQUOTA_ACCT))) {
+	    (mp->m_sb.sb_qflags & XFS_ALL_QUOTA_ACCT)) {
 		mp->m_qflags = 0;
 		goto write_changes;
 	}
@@ -509,7 +519,7 @@
  * Flush all dquots of the given file system to disk. The dquots are
  * _not_ purged from memory here, just their data written to disk.
  */
-int
+STATIC int
 xfs_qm_dqflush_all(
 	xfs_mount_t	*mp,
 	int		flags)
@@ -613,7 +623,7 @@
 STATIC int
 xfs_qm_dqpurge_int(
 	xfs_mount_t	*mp,
-	uint		flags) /* QUOTAOFF/UMOUNTING/UQUOTA/GQUOTA */
+	uint		flags) /* QUOTAOFF/UMOUNTING/UQUOTA/PQUOTA/GQUOTA */
 {
 	xfs_dquot_t	*dqp;
 	uint		dqtype;
@@ -625,6 +635,7 @@
 		return (0);
 
 	dqtype = (flags & XFS_QMOPT_UQUOTA) ? XFS_DQ_USER : 0;
+	dqtype |= (flags & XFS_QMOPT_PQUOTA) ? XFS_DQ_PROJ : 0;
 	dqtype |= (flags & XFS_QMOPT_GQUOTA) ? XFS_DQ_GROUP : 0;
 
 	xfs_qm_mplist_lock(mp);
@@ -734,11 +745,11 @@
 
 	/*
 	 * udqhint is the i_udquot field in inode, and is non-NULL only
-	 * when the type arg is XFS_DQ_GROUP. Its purpose is to save a
+	 * when the type arg is group/project. Its purpose is to save a
 	 * lookup by dqid (xfs_qm_dqget) by caching a group dquot inside
 	 * the user dquot.
 	 */
-	ASSERT(!udqhint || type == XFS_DQ_GROUP);
+	ASSERT(!udqhint || type == XFS_DQ_GROUP || type == XFS_DQ_PROJ);
 	if (udqhint && !dolock)
 		xfs_dqlock(udqhint);
 
@@ -897,8 +908,8 @@
 
 
 /*
- * Given a locked inode, attach dquot(s) to it, taking UQUOTAON / GQUOTAON
- * in to account.
+ * Given a locked inode, attach dquot(s) to it, taking U/G/P-QUOTAON
+ * into account.
  * If XFS_QMOPT_DQALLOC, the dquot(s) will be allocated if needed.
  * If XFS_QMOPT_DQLOCK, the dquot(s) will be returned locked. This option pretty
  * much made this code a complete mess, but it has been pretty useful.
@@ -937,8 +948,13 @@
 		nquotas++;
 	}
 	ASSERT(XFS_ISLOCKED_INODE_EXCL(ip));
-	if (XFS_IS_GQUOTA_ON(mp)) {
-		error = xfs_qm_dqattach_one(ip, ip->i_d.di_gid, XFS_DQ_GROUP,
+	if (XFS_IS_OQUOTA_ON(mp)) {
+		error = XFS_IS_GQUOTA_ON(mp) ?
+			xfs_qm_dqattach_one(ip, ip->i_d.di_gid, XFS_DQ_GROUP,
+						flags & XFS_QMOPT_DQALLOC,
+						flags & XFS_QMOPT_DQLOCK,
+						ip->i_udquot, &ip->i_gdquot) :
+			xfs_qm_dqattach_one(ip, ip->i_d.di_projid, XFS_DQ_PROJ,
 						flags & XFS_QMOPT_DQALLOC,
 						flags & XFS_QMOPT_DQLOCK,
 						ip->i_udquot, &ip->i_gdquot);
@@ -989,7 +1005,7 @@
 		}
 		if (XFS_IS_UQUOTA_ON(mp))
 			ASSERT(ip->i_udquot);
-		if (XFS_IS_GQUOTA_ON(mp))
+		if (XFS_IS_OQUOTA_ON(mp))
 			ASSERT(ip->i_gdquot);
 	}
 #endif
@@ -1018,13 +1034,13 @@
 
 	ASSERT(ip->i_ino != ip->i_mount->m_sb.sb_uquotino);
 	ASSERT(ip->i_ino != ip->i_mount->m_sb.sb_gquotino);
-	if (ip->i_udquot)
-		xfs_dqtrace_entry_ino(ip->i_udquot, "DQDETTACH", ip);
 	if (ip->i_udquot) {
+		xfs_dqtrace_entry_ino(ip->i_udquot, "DQDETTACH", ip);
 		xfs_qm_dqrele(ip->i_udquot);
 		ip->i_udquot = NULL;
 	}
 	if (ip->i_gdquot) {
+		xfs_dqtrace_entry_ino(ip->i_gdquot, "DQDETTACH", ip);
 		xfs_qm_dqrele(ip->i_gdquot);
 		ip->i_gdquot = NULL;
 	}
@@ -1149,7 +1165,7 @@
  * This initializes all the quota information that's kept in the
  * mount structure
  */
-int
+STATIC int
 xfs_qm_init_quotainfo(
 	xfs_mount_t	*mp)
 {
@@ -1202,8 +1218,9 @@
 	 * and group quotas, at least not at this point.
 	 */
 	error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)0,
-			     (XFS_IS_UQUOTA_RUNNING(mp)) ?
-			     XFS_DQ_USER : XFS_DQ_GROUP,
+			     XFS_IS_UQUOTA_RUNNING(mp) ? XFS_DQ_USER : 
+			     (XFS_IS_GQUOTA_RUNNING(mp) ? XFS_DQ_GROUP :
+				XFS_DQ_PROJ),
 			     XFS_QMOPT_DQSUSER|XFS_QMOPT_DOWARN,
 			     &dqp);
 	if (! error) {
@@ -1234,6 +1251,10 @@
 				INT_GET(ddqp->d_iwarns, ARCH_CONVERT) ?
 				INT_GET(ddqp->d_iwarns, ARCH_CONVERT) :
 				XFS_QM_IWARNLIMIT;
+		qinf->qi_rtbwarnlimit =
+				INT_GET(ddqp->d_rtbwarns, ARCH_CONVERT) ?
+				INT_GET(ddqp->d_rtbwarns, ARCH_CONVERT) :
+				XFS_QM_RTBWARNLIMIT;
 		qinf->qi_bhardlimit =
 				INT_GET(ddqp->d_blk_hardlimit, ARCH_CONVERT);
 		qinf->qi_bsoftlimit =
@@ -1259,6 +1280,7 @@
 		qinf->qi_rtbtimelimit = XFS_QM_RTBTIMELIMIT;
 		qinf->qi_bwarnlimit = XFS_QM_BWARNLIMIT;
 		qinf->qi_iwarnlimit = XFS_QM_IWARNLIMIT;
+		qinf->qi_rtbwarnlimit = XFS_QM_RTBWARNLIMIT;
 	}
 
 	return (0);
@@ -1366,13 +1388,20 @@
 		ASSERT(udqp);
 	}
 
-	if (XFS_IS_GQUOTA_ON(mp)) {
+	if (XFS_IS_OQUOTA_ON(mp)) {
 		ASSERT(ip->i_gdquot == NULL);
 		if (udqp)
 			xfs_dqunlock(udqp);
-		if ((error = xfs_qm_dqget(mp, ip, ip->i_d.di_gid, XFS_DQ_GROUP,
-					 XFS_QMOPT_DQALLOC|XFS_QMOPT_DOWARN,
-					 &gdqp))) {
+		error = XFS_IS_GQUOTA_ON(mp) ?
+				xfs_qm_dqget(mp, ip,
+					     ip->i_d.di_gid, XFS_DQ_GROUP,
+					     XFS_QMOPT_DQALLOC|XFS_QMOPT_DOWARN,
+					     &gdqp) :
+				xfs_qm_dqget(mp, ip,
+					     ip->i_d.di_projid, XFS_DQ_PROJ,
+					     XFS_QMOPT_DQALLOC|XFS_QMOPT_DOWARN,
+					     &gdqp);
+		if (error) {
 			if (udqp)
 				xfs_qm_dqrele(udqp);
 			ASSERT(error != ESRCH);
@@ -1521,8 +1550,10 @@
 		INT_SET(ddq->d_rtbcount, ARCH_CONVERT, 0ULL);
 		INT_SET(ddq->d_btimer, ARCH_CONVERT, (time_t)0);
 		INT_SET(ddq->d_itimer, ARCH_CONVERT, (time_t)0);
+		INT_SET(ddq->d_rtbtimer, ARCH_CONVERT, (time_t)0);
 		INT_SET(ddq->d_bwarns, ARCH_CONVERT, 0UL);
 		INT_SET(ddq->d_iwarns, ARCH_CONVERT, 0UL);
+		INT_SET(ddq->d_rtbwarns, ARCH_CONVERT, 0UL);
 		ddq = (xfs_disk_dquot_t *) ((xfs_dqblk_t *)ddq + 1);
 	}
 
@@ -1541,11 +1572,14 @@
 	int		error;
 	int		notcommitted;
 	int		incr;
+	int		type;
 
 	ASSERT(blkcnt > 0);
 	notcommitted = 0;
 	incr = (blkcnt > XFS_QM_MAX_DQCLUSTER_LOGSZ) ?
 		XFS_QM_MAX_DQCLUSTER_LOGSZ : blkcnt;
+	type = flags & XFS_QMOPT_UQUOTA ? XFS_DQ_USER :
+		(flags & XFS_QMOPT_PQUOTA ? XFS_DQ_PROJ : XFS_DQ_GROUP);
 	error = 0;
 
 	/*
@@ -1564,9 +1598,7 @@
 		if (error)
 			break;
 
-		(void) xfs_qm_reset_dqcounts(mp, bp, firstid,
-					     flags & XFS_QMOPT_UQUOTA ?
-					     XFS_DQ_USER : XFS_DQ_GROUP);
+		(void) xfs_qm_reset_dqcounts(mp, bp, firstid, type);
 		xfs_bdwrite(mp, bp);
 		/*
 		 * goto the next block.
@@ -1578,7 +1610,7 @@
 }
 
 /*
- * Iterate over all allocated USR/GRP dquots in the system, calling a
+ * Iterate over all allocated USR/GRP/PRJ dquots in the system, calling a
  * caller supplied function for every chunk of dquots that we find.
  */
 STATIC int
@@ -1849,7 +1881,7 @@
 		xfs_qm_quotacheck_dqadjust(udqp, nblks, rtblks);
 		xfs_qm_dqput(udqp);
 	}
-	if (XFS_IS_GQUOTA_ON(mp)) {
+	if (XFS_IS_OQUOTA_ON(mp)) {
 		ASSERT(gdqp);
 		xfs_qm_quotacheck_dqadjust(gdqp, nblks, rtblks);
 		xfs_qm_dqput(gdqp);
@@ -1898,7 +1930,7 @@
 	cmn_err(CE_NOTE, "XFS quotacheck %s: Please wait.", mp->m_fsname);
 
 	/*
-	 * First we go thru all the dquots on disk, USR and GRP, and reset
+	 * First we go thru all the dquots on disk, USR and GRP/PRJ, and reset
 	 * their counters to zero. We need a clean slate.
 	 * We don't log our changes till later.
 	 */
@@ -1909,9 +1941,10 @@
 	}
 
 	if ((gip = XFS_QI_GQIP(mp))) {
-		if ((error = xfs_qm_dqiterate(mp, gip, XFS_QMOPT_GQUOTA)))
+		if ((error = xfs_qm_dqiterate(mp, gip, XFS_IS_GQUOTA_ON(mp) ?
+					XFS_QMOPT_GQUOTA : XFS_QMOPT_PQUOTA)))
 			goto error_return;
-		flags |= XFS_GQUOTA_CHKD;
+		flags |= XFS_OQUOTA_CHKD;
 	}
 
 	do {
@@ -1938,7 +1971,7 @@
 	if (error) {
 		xfs_qm_dqpurge_all(mp,
 				   XFS_QMOPT_UQUOTA|XFS_QMOPT_GQUOTA|
-				   XFS_QMOPT_QUOTAOFF);
+				   XFS_QMOPT_PQUOTA|XFS_QMOPT_QUOTAOFF);
 		goto error_return;
 	}
 	/*
@@ -1961,7 +1994,7 @@
 	 * quotachecked status, since we won't be doing accounting for
 	 * that type anymore.
 	 */
-	mp->m_qflags &= ~(XFS_GQUOTA_CHKD | XFS_UQUOTA_CHKD);
+	mp->m_qflags &= ~(XFS_OQUOTA_CHKD | XFS_UQUOTA_CHKD);
 	mp->m_qflags |= flags;
 
 	XQM_LIST_PRINT(&(XFS_QI_MPL_LIST(mp)), MPL_NEXT, "++++ Mp list +++");
@@ -2013,7 +2046,7 @@
 					     0, 0, &uip, 0)))
 				return XFS_ERROR(error);
 		}
-		if (XFS_IS_GQUOTA_ON(mp) &&
+		if (XFS_IS_OQUOTA_ON(mp) &&
 		    mp->m_sb.sb_gquotino != NULLFSINO) {
 			ASSERT(mp->m_sb.sb_gquotino > 0);
 			if ((error = xfs_iget(mp, NULL, mp->m_sb.sb_gquotino,
@@ -2043,10 +2076,12 @@
 
 		flags &= ~XFS_QMOPT_SBVERSION;
 	}
-	if (XFS_IS_GQUOTA_ON(mp) && gip == NULL) {
-		if ((error = xfs_qm_qino_alloc(mp, &gip,
-					      sbflags | XFS_SB_GQUOTINO,
-					      flags | XFS_QMOPT_GQUOTA))) {
+	if (XFS_IS_OQUOTA_ON(mp) && gip == NULL) {
+		flags |= (XFS_IS_GQUOTA_ON(mp) ?
+				XFS_QMOPT_GQUOTA : XFS_QMOPT_PQUOTA);
+		error = xfs_qm_qino_alloc(mp, &gip,
+					  sbflags | XFS_SB_GQUOTINO, flags);
+		if (error) {
 			if (uip)
 				VN_RELE(XFS_ITOV(uip));
 
@@ -2452,6 +2487,7 @@
 	xfs_inode_t	*ip,
 	uid_t		uid,
 	gid_t		gid,
+	prid_t		prid,
 	uint		flags,
 	xfs_dquot_t	**O_udqpp,
 	xfs_dquot_t	**O_gdqpp)
@@ -2483,8 +2519,7 @@
 	}
 
 	uq = gq = NULL;
-	if ((flags & XFS_QMOPT_UQUOTA) &&
-	    XFS_IS_UQUOTA_ON(mp)) {
+	if ((flags & XFS_QMOPT_UQUOTA) && XFS_IS_UQUOTA_ON(mp)) {
 		if (ip->i_d.di_uid != uid) {
 			/*
 			 * What we need is the dquot that has this uid, and
@@ -2522,8 +2557,7 @@
 			xfs_dqunlock(uq);
 		}
 	}
-	if ((flags & XFS_QMOPT_GQUOTA) &&
-	    XFS_IS_GQUOTA_ON(mp)) {
+	if ((flags & XFS_QMOPT_GQUOTA) && XFS_IS_GQUOTA_ON(mp)) {
 		if (ip->i_d.di_gid != gid) {
 			xfs_iunlock(ip, lockflags);
 			if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)gid,
@@ -2546,6 +2580,29 @@
 			XFS_DQHOLD(gq);
 			xfs_dqunlock(gq);
 		}
+	} else if ((flags & XFS_QMOPT_PQUOTA) && XFS_IS_PQUOTA_ON(mp)) {
+		if (ip->i_d.di_projid != prid) {
+			xfs_iunlock(ip, lockflags);
+			if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)prid,
+						 XFS_DQ_PROJ,
+						 XFS_QMOPT_DQALLOC |
+						 XFS_QMOPT_DOWARN,
+						 &gq))) {
+				if (uq)
+					xfs_qm_dqrele(uq);
+				ASSERT(error != ENOENT);
+				return (error);
+			}
+			xfs_dqunlock(gq);
+			lockflags = XFS_ILOCK_SHARED;
+			xfs_ilock(ip, lockflags);
+		} else {
+			ASSERT(ip->i_gdquot);
+			gq = ip->i_gdquot;
+			xfs_dqlock(gq);
+			XFS_DQHOLD(gq);
+			xfs_dqunlock(gq);
+		}
 	}
 	if (uq)
 		xfs_dqtrace_entry_ino(uq, "DQALLOC", ip);
@@ -2574,6 +2631,9 @@
 	xfs_dquot_t	*newdq)
 {
 	xfs_dquot_t	*prevdq;
+	uint		bfield = XFS_IS_REALTIME_INODE(ip) ?
+				 XFS_TRANS_DQ_RTBCOUNT : XFS_TRANS_DQ_BCOUNT;
+
 	ASSERT(XFS_ISLOCKED_INODE_EXCL(ip));
 	ASSERT(XFS_IS_QUOTA_RUNNING(ip->i_mount));
 
@@ -2582,20 +2642,12 @@
 	ASSERT(prevdq);
 	ASSERT(prevdq != newdq);
 
-	xfs_trans_mod_dquot(tp, prevdq,
-			    XFS_TRANS_DQ_BCOUNT,
-			    -(ip->i_d.di_nblocks));
-	xfs_trans_mod_dquot(tp, prevdq,
-			    XFS_TRANS_DQ_ICOUNT,
-			    -1);
+	xfs_trans_mod_dquot(tp, prevdq, bfield, -(ip->i_d.di_nblocks));
+	xfs_trans_mod_dquot(tp, prevdq, XFS_TRANS_DQ_ICOUNT, -1);
 
 	/* the sparkling new dquot */
-	xfs_trans_mod_dquot(tp, newdq,
-			    XFS_TRANS_DQ_BCOUNT,
-			    ip->i_d.di_nblocks);
-	xfs_trans_mod_dquot(tp, newdq,
-			    XFS_TRANS_DQ_ICOUNT,
-			    1);
+	xfs_trans_mod_dquot(tp, newdq, bfield, ip->i_d.di_nblocks);
+	xfs_trans_mod_dquot(tp, newdq, XFS_TRANS_DQ_ICOUNT, 1);
 
 	/*
 	 * Take an extra reference, because the inode
@@ -2611,7 +2663,7 @@
 }
 
 /*
- * Quota reservations for setattr(AT_UID|AT_GID).
+ * Quota reservations for setattr(AT_UID|AT_GID|AT_PROJID).
  */
 int
 xfs_qm_vop_chown_reserve(
@@ -2623,7 +2675,7 @@
 {
 	int		error;
 	xfs_mount_t	*mp;
-	uint		delblks;
+	uint		delblks, blkflags;
 	xfs_dquot_t	*unresudq, *unresgdq, *delblksudq, *delblksgdq;
 
 	ASSERT(XFS_ISLOCKED_INODE(ip));
@@ -2632,6 +2684,8 @@
 
 	delblks = ip->i_delayed_blks;
 	delblksudq = delblksgdq = unresudq = unresgdq = NULL;
+	blkflags = XFS_IS_REALTIME_INODE(ip) ?
+			XFS_QMOPT_RES_RTBLKS : XFS_QMOPT_RES_REGBLKS;
 
 	if (XFS_IS_UQUOTA_ON(mp) && udqp &&
 	    ip->i_d.di_uid != (uid_t)INT_GET(udqp->q_core.d_id, ARCH_CONVERT)) {
@@ -2646,18 +2700,22 @@
 			unresudq = ip->i_udquot;
 		}
 	}
-	if (XFS_IS_GQUOTA_ON(ip->i_mount) && gdqp &&
-	    ip->i_d.di_gid != INT_GET(gdqp->q_core.d_id, ARCH_CONVERT)) {
-		delblksgdq = gdqp;
-		if (delblks) {
-			ASSERT(ip->i_gdquot);
-			unresgdq = ip->i_gdquot;
+	if (XFS_IS_OQUOTA_ON(ip->i_mount) && gdqp) {
+		if ((XFS_IS_GQUOTA_ON(ip->i_mount) && ip->i_d.di_gid !=
+				INT_GET(gdqp->q_core.d_id, ARCH_CONVERT)) ||
+		    (XFS_IS_PQUOTA_ON(ip->i_mount) && ip->i_d.di_projid !=
+				INT_GET(gdqp->q_core.d_id, ARCH_CONVERT))) {
+			delblksgdq = gdqp;
+			if (delblks) {
+				ASSERT(ip->i_gdquot);
+				unresgdq = ip->i_gdquot;
+			}
 		}
 	}
 
 	if ((error = xfs_trans_reserve_quota_bydquots(tp, ip->i_mount,
 				delblksudq, delblksgdq, ip->i_d.di_nblocks, 1,
-				flags | XFS_QMOPT_RES_REGBLKS)))
+				flags | blkflags)))
 		return (error);
 
 	/*
@@ -2674,11 +2732,11 @@
 		ASSERT(unresudq || unresgdq);
 		if ((error = xfs_trans_reserve_quota_bydquots(NULL, ip->i_mount,
 				delblksudq, delblksgdq, (xfs_qcnt_t)delblks, 0,
-				flags | XFS_QMOPT_RES_REGBLKS)))
+				flags | blkflags)))
 			return (error);
 		xfs_trans_reserve_quota_bydquots(NULL, ip->i_mount,
 				unresudq, unresgdq, -((xfs_qcnt_t)delblks), 0,
-				XFS_QMOPT_RES_REGBLKS);
+				blkflags);
 	}
 
 	return (0);
@@ -2751,7 +2809,7 @@
 }
 
 /* ------------- list stuff -----------------*/
-void
+STATIC void
 xfs_qm_freelist_init(xfs_frlist_t *ql)
 {
 	ql->qh_next = ql->qh_prev = (xfs_dquot_t *) ql;
@@ -2760,7 +2818,7 @@
 	ql->qh_nelems = 0;
 }
 
-void
+STATIC void
 xfs_qm_freelist_destroy(xfs_frlist_t *ql)
 {
 	xfs_dquot_t	*dqp, *nextdqp;
@@ -2786,7 +2844,7 @@
 	ASSERT(ql->qh_nelems == 0);
 }
 
-void
+STATIC void
 xfs_qm_freelist_insert(xfs_frlist_t *ql, xfs_dquot_t *dq)
 {
 	dq->dq_flnext = ql->qh_next;
@@ -2816,7 +2874,7 @@
 	xfs_qm_freelist_insert((xfs_frlist_t *)ql->qh_prev, dq);
 }
 
-int
+STATIC int
 xfs_qm_dqhashlock_nowait(
 	xfs_dquot_t *dqp)
 {
@@ -2836,7 +2894,7 @@
 	return (locked);
 }
 
-int
+STATIC int
 xfs_qm_mplist_nowait(
 	xfs_mount_t	*mp)
 {
diff --git a/fs/xfs/quota/xfs_qm.h b/fs/xfs/quota/xfs_qm.h
index dcf1a7a..b03eecf 100644
--- a/fs/xfs/quota/xfs_qm.h
+++ b/fs/xfs/quota/xfs_qm.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000-2004 Silicon Graphics, Inc.  All Rights Reserved.
+ * Copyright (c) 2000-2005 Silicon Graphics, Inc.  All Rights Reserved.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms of version 2 of the GNU General Public License as
@@ -133,8 +133,9 @@
 	time_t		 qi_btimelimit;	 /* limit for blks timer */
 	time_t		 qi_itimelimit;	 /* limit for inodes timer */
 	time_t		 qi_rtbtimelimit;/* limit for rt blks timer */
-	xfs_qwarncnt_t	 qi_bwarnlimit;	 /* limit for num warnings */
-	xfs_qwarncnt_t	 qi_iwarnlimit;	 /* limit for num warnings */
+	xfs_qwarncnt_t	 qi_bwarnlimit;	 /* limit for blks warnings */
+	xfs_qwarncnt_t	 qi_iwarnlimit;	 /* limit for inodes warnings */
+	xfs_qwarncnt_t	 qi_rtbwarnlimit;/* limit for rt blks warnings */
 	mutex_t		 qi_quotaofflock;/* to serialize quotaoff */
 	xfs_filblks_t	 qi_dqchunklen;	 /* # BBs in a chunk of dqs */
 	uint		 qi_dqperchunk;	 /* # ondisk dqs in above chunk */
@@ -176,6 +177,7 @@
 
 #define XFS_QM_BWARNLIMIT	5
 #define XFS_QM_IWARNLIMIT	5
+#define XFS_QM_RTBWARNLIMIT	5
 
 #define XFS_QM_LOCK(xqm)	(mutex_lock(&xqm##_lock, PINOD))
 #define XFS_QM_UNLOCK(xqm)	(mutex_unlock(&xqm##_lock))
@@ -184,7 +186,6 @@
 
 extern void		xfs_mount_reset_sbqflags(xfs_mount_t *);
 
-extern int		xfs_qm_init_quotainfo(xfs_mount_t *);
 extern void		xfs_qm_destroy_quotainfo(xfs_mount_t *);
 extern int		xfs_qm_mount_quotas(xfs_mount_t *, int);
 extern void		xfs_qm_mount_quotainit(xfs_mount_t *, uint);
@@ -203,7 +204,7 @@
 
 /* vop stuff */
 extern int		xfs_qm_vop_dqalloc(xfs_mount_t *, xfs_inode_t *,
-					uid_t, gid_t, uint,
+					uid_t, gid_t, prid_t, uint,
 					xfs_dquot_t **, xfs_dquot_t **);
 extern void		xfs_qm_vop_dqattach_and_dqmod_newinode(
 					xfs_trans_t *, xfs_inode_t *,
@@ -215,14 +216,9 @@
 					xfs_dquot_t *, xfs_dquot_t *, uint);
 
 /* list stuff */
-extern void		xfs_qm_freelist_init(xfs_frlist_t *);
-extern void		xfs_qm_freelist_destroy(xfs_frlist_t *);
-extern void		xfs_qm_freelist_insert(xfs_frlist_t *, xfs_dquot_t *);
 extern void		xfs_qm_freelist_append(xfs_frlist_t *, xfs_dquot_t *);
 extern void		xfs_qm_freelist_unlink(xfs_dquot_t *);
 extern int		xfs_qm_freelist_lock_nowait(xfs_qm_t *);
-extern int		xfs_qm_mplist_nowait(xfs_mount_t *);
-extern int		xfs_qm_dqhashlock_nowait(xfs_dquot_t *);
 
 /* system call interface */
 extern int		xfs_qm_quotactl(bhv_desc_t *, int, int, xfs_caddr_t);
diff --git a/fs/xfs/quota/xfs_qm_bhv.c b/fs/xfs/quota/xfs_qm_bhv.c
index be67d9c..dc3c37a 100644
--- a/fs/xfs/quota/xfs_qm_bhv.c
+++ b/fs/xfs/quota/xfs_qm_bhv.c
@@ -71,10 +71,13 @@
 #define MNTOPT_NOQUOTA	"noquota"	/* no quotas */
 #define MNTOPT_USRQUOTA	"usrquota"	/* user quota enabled */
 #define MNTOPT_GRPQUOTA	"grpquota"	/* group quota enabled */
+#define MNTOPT_PRJQUOTA	"prjquota"	/* project quota enabled */
 #define MNTOPT_UQUOTA	"uquota"	/* user quota (IRIX variant) */
 #define MNTOPT_GQUOTA	"gquota"	/* group quota (IRIX variant) */
+#define MNTOPT_PQUOTA	"pquota"	/* project quota (IRIX variant) */
 #define MNTOPT_UQUOTANOENF "uqnoenforce"/* user quota limit enforcement */
 #define MNTOPT_GQUOTANOENF "gqnoenforce"/* group quota limit enforcement */
+#define MNTOPT_PQUOTANOENF "pqnoenforce"/* project quota limit enforcement */
 #define MNTOPT_QUOTANOENF  "qnoenforce"	/* same as uqnoenforce */
 
 STATIC int
@@ -109,6 +112,14 @@
 			args->flags |= XFSMNT_UQUOTA;
 			args->flags &= ~XFSMNT_UQUOTAENF;
 			referenced = 1;
+		} else if (!strcmp(this_char, MNTOPT_PQUOTA) ||
+			   !strcmp(this_char, MNTOPT_PRJQUOTA)) {
+			args->flags |= XFSMNT_PQUOTA | XFSMNT_PQUOTAENF;
+			referenced = 1;
+		} else if (!strcmp(this_char, MNTOPT_PQUOTANOENF)) {
+			args->flags |= XFSMNT_PQUOTA;
+			args->flags &= ~XFSMNT_PQUOTAENF;
+			referenced = 1;
 		} else if (!strcmp(this_char, MNTOPT_GQUOTA) ||
 			   !strcmp(this_char, MNTOPT_GRPQUOTA)) {
 			args->flags |= XFSMNT_GQUOTA | XFSMNT_GQUOTAENF;
@@ -127,6 +138,12 @@
 			*this_char++ = ',';
 	}
 
+	if ((args->flags & XFSMNT_GQUOTA) && (args->flags & XFSMNT_PQUOTA)) {
+		cmn_err(CE_WARN,
+			"XFS: cannot mount with both project and group quota");
+		return XFS_ERROR(EINVAL);
+	}
+
 	PVFS_PARSEARGS(BHV_NEXT(bhv), options, args, update, error);
 	if (!error && !referenced)
 		bhv_remove_vfsops(bhvtovfs(bhv), VFS_POSITION_QM);
@@ -148,13 +165,19 @@
 			seq_puts(m, "," MNTOPT_UQUOTANOENF);
 	}
 
+	if (mp->m_qflags & XFS_PQUOTA_ACCT) {
+		(mp->m_qflags & XFS_OQUOTA_ENFD) ?
+			seq_puts(m, "," MNTOPT_PRJQUOTA) :
+			seq_puts(m, "," MNTOPT_PQUOTANOENF);
+	}
+
 	if (mp->m_qflags & XFS_GQUOTA_ACCT) {
-		(mp->m_qflags & XFS_GQUOTA_ENFD) ?
+		(mp->m_qflags & XFS_OQUOTA_ENFD) ?
 			seq_puts(m, "," MNTOPT_GRPQUOTA) :
 			seq_puts(m, "," MNTOPT_GQUOTANOENF);
 	}
 
-	if (!(mp->m_qflags & (XFS_UQUOTA_ACCT|XFS_GQUOTA_ACCT)))
+	if (!(mp->m_qflags & XFS_ALL_QUOTA_ACCT))
 		seq_puts(m, "," MNTOPT_NOQUOTA);
 
 	PVFS_SHOWARGS(BHV_NEXT(bhv), m, error);
@@ -171,7 +194,7 @@
 	struct xfs_mount	*mp = XFS_VFSTOM(vfsp);
 	int			error;
 
-	if (args->flags & (XFSMNT_UQUOTA | XFSMNT_GQUOTA))
+	if (args->flags & (XFSMNT_UQUOTA | XFSMNT_GQUOTA | XFSMNT_PQUOTA))
 		xfs_qm_mount_quotainit(mp, args->flags);
 	PVFS_MOUNT(BHV_NEXT(bhv), args, cr, error);
 	return error;
@@ -255,16 +278,17 @@
 	uint		*quotaflags)
 {
 	uint		quotaondisk;
-	uint		uquotaondisk = 0, gquotaondisk = 0;
+	uint		uquotaondisk = 0, gquotaondisk = 0, pquotaondisk = 0;
 
 	*quotaflags = 0;
 	*needquotamount = B_FALSE;
 
 	quotaondisk = XFS_SB_VERSION_HASQUOTA(&mp->m_sb) &&
-		mp->m_sb.sb_qflags & (XFS_UQUOTA_ACCT|XFS_GQUOTA_ACCT);
+				(mp->m_sb.sb_qflags & XFS_ALL_QUOTA_ACCT);
 
 	if (quotaondisk) {
 		uquotaondisk = mp->m_sb.sb_qflags & XFS_UQUOTA_ACCT;
+		pquotaondisk = mp->m_sb.sb_qflags & XFS_PQUOTA_ACCT;
 		gquotaondisk = mp->m_sb.sb_qflags & XFS_GQUOTA_ACCT;
 	}
 
@@ -277,13 +301,16 @@
 
 	if (((uquotaondisk && !XFS_IS_UQUOTA_ON(mp)) ||
 	    (!uquotaondisk &&  XFS_IS_UQUOTA_ON(mp)) ||
+	     (pquotaondisk && !XFS_IS_PQUOTA_ON(mp)) ||
+	    (!pquotaondisk &&  XFS_IS_PQUOTA_ON(mp)) ||
 	     (gquotaondisk && !XFS_IS_GQUOTA_ON(mp)) ||
-	    (!gquotaondisk &&  XFS_IS_GQUOTA_ON(mp)))  &&
+	    (!gquotaondisk &&  XFS_IS_OQUOTA_ON(mp)))  &&
 	    xfs_dev_is_read_only(mp, "changing quota state")) {
 		cmn_err(CE_WARN,
-			"XFS: please mount with%s%s%s.",
+			"XFS: please mount with%s%s%s%s.",
 			(!quotaondisk ? "out quota" : ""),
 			(uquotaondisk ? " usrquota" : ""),
+			(pquotaondisk ? " prjquota" : ""),
 			(gquotaondisk ? " grpquota" : ""));
 		return XFS_ERROR(EPERM);
 	}
@@ -359,7 +386,7 @@
 }
 
 
-struct xfs_qmops xfs_qmcore_xfs = {
+STATIC struct xfs_qmops xfs_qmcore_xfs = {
 	.xfs_qminit		= xfs_qm_newmount,
 	.xfs_qmdone		= xfs_qm_unmount_quotadestroy,
 	.xfs_qmmount		= xfs_qm_endmount,
diff --git a/fs/xfs/quota/xfs_qm_syscalls.c b/fs/xfs/quota/xfs_qm_syscalls.c
index 229f5b5..68e9896 100644
--- a/fs/xfs/quota/xfs_qm_syscalls.c
+++ b/fs/xfs/quota/xfs_qm_syscalls.c
@@ -118,40 +118,41 @@
 	 * The following commands are valid even when quotaoff.
 	 */
 	switch (cmd) {
+	case Q_XQUOTARM:
 		/*
-		 * truncate quota files. quota must be off.
+		 * Truncate quota files. quota must be off.
 		 */
-	      case Q_XQUOTARM:
 		if (XFS_IS_QUOTA_ON(mp) || addr == NULL)
 			return XFS_ERROR(EINVAL);
 		if (vfsp->vfs_flag & VFS_RDONLY)
 			return XFS_ERROR(EROFS);
 		return (xfs_qm_scall_trunc_qfiles(mp,
 			       xfs_qm_import_qtype_flags(*(uint *)addr)));
+
+	case Q_XGETQSTAT:
 		/*
 		 * Get quota status information.
 		 */
-	      case Q_XGETQSTAT:
 		return (xfs_qm_scall_getqstat(mp, (fs_quota_stat_t *)addr));
 
+	case Q_XQUOTAON:
 		/*
-		 * QUOTAON for root f/s and quota enforcement on others..
-		 * Quota accounting for non-root f/s's must be turned on
-		 * at mount time.
+		 * QUOTAON - enabling quota enforcement.
+		 * Quota accounting must be turned on at mount time.
 		 */
-	      case Q_XQUOTAON:
 		if (addr == NULL)
 			return XFS_ERROR(EINVAL);
 		if (vfsp->vfs_flag & VFS_RDONLY)
 			return XFS_ERROR(EROFS);
 		return (xfs_qm_scall_quotaon(mp,
 					  xfs_qm_import_flags(*(uint *)addr)));
-	      case Q_XQUOTAOFF:
+
+	case Q_XQUOTAOFF:
 		if (vfsp->vfs_flag & VFS_RDONLY)
 			return XFS_ERROR(EROFS);
 		break;
 
-	      default:
+	default:
 		break;
 	}
 
@@ -159,7 +160,7 @@
 		return XFS_ERROR(ESRCH);
 
 	switch (cmd) {
-	      case Q_XQUOTAOFF:
+	case Q_XQUOTAOFF:
 		if (vfsp->vfs_flag & VFS_RDONLY)
 			return XFS_ERROR(EROFS);
 		error = xfs_qm_scall_quotaoff(mp,
@@ -167,42 +168,39 @@
 					    B_FALSE);
 		break;
 
-		/*
-		 * Defaults to XFS_GETUQUOTA.
-		 */
-	      case Q_XGETQUOTA:
+	case Q_XGETQUOTA:
 		error = xfs_qm_scall_getquota(mp, (xfs_dqid_t)id, XFS_DQ_USER,
 					(fs_disk_quota_t *)addr);
 		break;
-		/*
-		 * Set limits, both hard and soft. Defaults to Q_SETUQLIM.
-		 */
-	      case Q_XSETQLIM:
+	case Q_XGETGQUOTA:
+		error = xfs_qm_scall_getquota(mp, (xfs_dqid_t)id, XFS_DQ_GROUP,
+					(fs_disk_quota_t *)addr);
+		break;
+	case Q_XGETPQUOTA:
+		error = xfs_qm_scall_getquota(mp, (xfs_dqid_t)id, XFS_DQ_PROJ,
+					(fs_disk_quota_t *)addr);
+		break;
+
+	case Q_XSETQLIM:
 		if (vfsp->vfs_flag & VFS_RDONLY)
 			return XFS_ERROR(EROFS);
 		error = xfs_qm_scall_setqlim(mp, (xfs_dqid_t)id, XFS_DQ_USER,
 					     (fs_disk_quota_t *)addr);
 		break;
-
-	       case Q_XSETGQLIM:
+	case Q_XSETGQLIM:
 		if (vfsp->vfs_flag & VFS_RDONLY)
 			return XFS_ERROR(EROFS);
 		error = xfs_qm_scall_setqlim(mp, (xfs_dqid_t)id, XFS_DQ_GROUP,
 					     (fs_disk_quota_t *)addr);
 		break;
-
-
-	      case Q_XGETGQUOTA:
-		error = xfs_qm_scall_getquota(mp, (xfs_dqid_t)id, XFS_DQ_GROUP,
-					(fs_disk_quota_t *)addr);
+	case Q_XSETPQLIM:
+		if (vfsp->vfs_flag & VFS_RDONLY)
+			return XFS_ERROR(EROFS);
+		error = xfs_qm_scall_setqlim(mp, (xfs_dqid_t)id, XFS_DQ_PROJ,
+					     (fs_disk_quota_t *)addr);
 		break;
 
-		/*
-		 * Quotas are entirely undefined after quotaoff in XFS quotas.
-		 * For instance, there's no way to set limits when quotaoff.
-		 */
-
-	      default:
+	default:
 		error = XFS_ERROR(EINVAL);
 		break;
 	}
@@ -286,8 +284,12 @@
 	}
 	if (flags & XFS_GQUOTA_ACCT) {
 		dqtype |= XFS_QMOPT_GQUOTA;
-		flags |= (XFS_GQUOTA_CHKD | XFS_GQUOTA_ENFD);
+		flags |= (XFS_OQUOTA_CHKD | XFS_OQUOTA_ENFD);
 		inactivate_flags |= XFS_GQUOTA_ACTIVE;
+	} else if (flags & XFS_PQUOTA_ACCT) {
+		dqtype |= XFS_QMOPT_PQUOTA;
+		flags |= (XFS_OQUOTA_CHKD | XFS_OQUOTA_ENFD);
+		inactivate_flags |= XFS_PQUOTA_ACTIVE;
 	}
 
 	/*
@@ -364,7 +366,8 @@
 	/*
 	 * If quotas is completely disabled, close shop.
 	 */
-	if ((flags & XFS_MOUNT_QUOTA_ALL) == XFS_MOUNT_QUOTA_ALL) {
+	if (((flags & XFS_MOUNT_QUOTA_ALL) == XFS_MOUNT_QUOTA_SET1) ||
+	    ((flags & XFS_MOUNT_QUOTA_ALL) == XFS_MOUNT_QUOTA_SET2)) {
 		mutex_unlock(&(XFS_QI_QOFFLOCK(mp)));
 		xfs_qm_destroy_quotainfo(mp);
 		return (0);
@@ -378,7 +381,7 @@
 		XFS_PURGE_INODE(XFS_QI_UQIP(mp));
 		XFS_QI_UQIP(mp) = NULL;
 	}
-	if ((dqtype & XFS_QMOPT_GQUOTA) && XFS_QI_GQIP(mp)) {
+	if ((dqtype & (XFS_QMOPT_GQUOTA|XFS_QMOPT_PQUOTA)) && XFS_QI_GQIP(mp)) {
 		XFS_PURGE_INODE(XFS_QI_GQIP(mp));
 		XFS_QI_GQIP(mp) = NULL;
 	}
@@ -411,7 +414,8 @@
 		}
 	}
 
-	if ((flags & XFS_DQ_GROUP) && mp->m_sb.sb_gquotino != NULLFSINO) {
+	if ((flags & (XFS_DQ_GROUP|XFS_DQ_PROJ)) &&
+	    mp->m_sb.sb_gquotino != NULLFSINO) {
 		error = xfs_iget(mp, NULL, mp->m_sb.sb_gquotino, 0, 0, &qip, 0);
 		if (! error) {
 			(void) xfs_truncate_file(mp, qip);
@@ -434,7 +438,7 @@
 	uint		flags)
 {
 	int		error;
-	unsigned long s;
+	unsigned long	s;
 	uint		qf;
 	uint		accflags;
 	__int64_t	sbflags;
@@ -468,9 +472,13 @@
 	    (mp->m_sb.sb_qflags & XFS_UQUOTA_ACCT) == 0 &&
 	    (flags & XFS_UQUOTA_ENFD))
 	    ||
+	    ((flags & XFS_PQUOTA_ACCT) == 0 &&
+	    (mp->m_sb.sb_qflags & XFS_PQUOTA_ACCT) == 0 &&
+	    (flags & XFS_OQUOTA_ENFD))
+	    ||
 	    ((flags & XFS_GQUOTA_ACCT) == 0 &&
 	    (mp->m_sb.sb_qflags & XFS_GQUOTA_ACCT) == 0 &&
-	    (flags & XFS_GQUOTA_ENFD))) {
+	    (flags & XFS_OQUOTA_ENFD))) {
 		qdprintk("Can't enforce without acct, flags=%x sbflags=%x\n",
 			flags, mp->m_sb.sb_qflags);
 		return XFS_ERROR(EINVAL);
@@ -504,6 +512,10 @@
 	 */
 	if  (((mp->m_sb.sb_qflags & XFS_UQUOTA_ACCT) !=
 	     (mp->m_qflags & XFS_UQUOTA_ACCT)) ||
+	     ((mp->m_sb.sb_qflags & XFS_PQUOTA_ACCT) !=
+	     (mp->m_qflags & XFS_PQUOTA_ACCT)) ||
+	     ((mp->m_sb.sb_qflags & XFS_GQUOTA_ACCT) !=
+	     (mp->m_qflags & XFS_GQUOTA_ACCT)) ||
 	    (flags & XFS_ALL_QUOTA_ENFD) == 0)
 		return (0);
 
@@ -521,7 +533,6 @@
 }
 
 
-
 /*
  * Return quota status information, such as uquota-off, enforcements, etc.
  */
@@ -606,7 +617,8 @@
 	if (!capable(CAP_SYS_ADMIN))
 		return XFS_ERROR(EPERM);
 
-	if ((newlim->d_fieldmask & (FS_DQ_LIMIT_MASK|FS_DQ_TIMER_MASK)) == 0)
+	if ((newlim->d_fieldmask &
+	    (FS_DQ_LIMIT_MASK|FS_DQ_TIMER_MASK|FS_DQ_WARNS_MASK)) == 0)
 		return (0);
 
 	tp = xfs_trans_alloc(mp, XFS_TRANS_QM_SETQLIM);
@@ -691,12 +703,23 @@
 		qdprintk("ihard %Ld < isoft %Ld\n", hard, soft);
 	}
 
+	/*
+	 * Update warnings counter(s) if requested
+	 */
+	if (newlim->d_fieldmask & FS_DQ_BWARNS)
+		INT_SET(ddq->d_bwarns, ARCH_CONVERT, newlim->d_bwarns);
+	if (newlim->d_fieldmask & FS_DQ_IWARNS)
+		INT_SET(ddq->d_iwarns, ARCH_CONVERT, newlim->d_iwarns);
+	if (newlim->d_fieldmask & FS_DQ_RTBWARNS)
+		INT_SET(ddq->d_rtbwarns, ARCH_CONVERT, newlim->d_rtbwarns);
+
 	if (id == 0) {
 		/*
 		 * Timelimits for the super user set the relative time
 		 * the other users can be over quota for this file system.
 		 * If it is zero a default is used.  Ditto for the default
-		 * soft and hard limit values (already done, above).
+		 * soft and hard limit values (already done, above), and
+		 * for warnings.
 		 */
 		if (newlim->d_fieldmask & FS_DQ_BTIMER) {
 			mp->m_quotainfo->qi_btimelimit = newlim->d_btimer;
@@ -710,7 +733,13 @@
 			mp->m_quotainfo->qi_rtbtimelimit = newlim->d_rtbtimer;
 			INT_SET(ddq->d_rtbtimer, ARCH_CONVERT, newlim->d_rtbtimer);
 		}
-	} else /* if (XFS_IS_QUOTA_ENFORCED(mp)) */ {
+		if (newlim->d_fieldmask & FS_DQ_BWARNS)
+			mp->m_quotainfo->qi_bwarnlimit = newlim->d_bwarns;
+		if (newlim->d_fieldmask & FS_DQ_IWARNS)
+			mp->m_quotainfo->qi_iwarnlimit = newlim->d_iwarns;
+		if (newlim->d_fieldmask & FS_DQ_RTBWARNS)
+			mp->m_quotainfo->qi_rtbwarnlimit = newlim->d_rtbwarns;
+	} else {
 		/*
 		 * If the user is now over quota, start the timelimit.
 		 * The user will not be 'warned'.
@@ -776,9 +805,9 @@
 	xfs_qoff_logitem_t	*startqoff,
 	uint			flags)
 {
-	xfs_trans_t	       *tp;
+	xfs_trans_t		*tp;
 	int			error;
-	xfs_qoff_logitem_t     *qoffi;
+	xfs_qoff_logitem_t	*qoffi;
 
 	tp = xfs_trans_alloc(mp, XFS_TRANS_QM_QUOTAOFF_END);
 
@@ -928,18 +957,26 @@
 
 STATIC uint
 xfs_qm_import_qtype_flags(
-	uint uflags)
+	uint		uflags)
 {
+	uint		oflags = 0;
+
 	/*
-	 * Can't be both at the same time.
+	 * Can't be more than one, or none.
 	 */
 	if (((uflags & (XFS_GROUP_QUOTA | XFS_USER_QUOTA)) ==
-	     (XFS_GROUP_QUOTA | XFS_USER_QUOTA)) ||
-	    ((uflags & (XFS_GROUP_QUOTA | XFS_USER_QUOTA)) == 0))
+			(XFS_GROUP_QUOTA | XFS_USER_QUOTA)) ||
+	    ((uflags & (XFS_GROUP_QUOTA | XFS_PROJ_QUOTA)) ==
+			(XFS_GROUP_QUOTA | XFS_PROJ_QUOTA)) ||
+	    ((uflags & (XFS_USER_QUOTA | XFS_PROJ_QUOTA)) ==
+			(XFS_USER_QUOTA | XFS_PROJ_QUOTA)) ||
+	    ((uflags & (XFS_GROUP_QUOTA|XFS_USER_QUOTA|XFS_PROJ_QUOTA)) == 0))
 		return (0);
 
-	return (uflags & XFS_USER_QUOTA) ?
-		XFS_DQ_USER : XFS_DQ_GROUP;
+	oflags |= (uflags & XFS_USER_QUOTA) ? XFS_DQ_USER : 0;
+	oflags |= (uflags & XFS_PROJ_QUOTA) ? XFS_DQ_PROJ : 0;
+	oflags |= (uflags & XFS_GROUP_QUOTA) ? XFS_DQ_GROUP: 0;
+	return oflags;
 }
 
 STATIC uint
@@ -947,14 +984,19 @@
 	uint flags)
 {
 	/*
-	 * Can't be both at the same time.
+	 * Can't be more than one, or none.
 	 */
-	ASSERT((flags & (XFS_GROUP_QUOTA | XFS_USER_QUOTA)) !=
-		(XFS_GROUP_QUOTA | XFS_USER_QUOTA));
-	ASSERT((flags & (XFS_GROUP_QUOTA | XFS_USER_QUOTA)) != 0);
+	ASSERT((flags & (XFS_PROJ_QUOTA | XFS_USER_QUOTA)) !=
+		(XFS_PROJ_QUOTA | XFS_USER_QUOTA));
+	ASSERT((flags & (XFS_PROJ_QUOTA | XFS_GROUP_QUOTA)) !=
+		(XFS_PROJ_QUOTA | XFS_GROUP_QUOTA));
+	ASSERT((flags & (XFS_USER_QUOTA | XFS_GROUP_QUOTA)) !=
+		(XFS_USER_QUOTA | XFS_GROUP_QUOTA));
+	ASSERT((flags & (XFS_PROJ_QUOTA|XFS_USER_QUOTA|XFS_GROUP_QUOTA)) != 0);
 
 	return (flags & XFS_DQ_USER) ?
-		XFS_USER_QUOTA : XFS_GROUP_QUOTA;
+		XFS_USER_QUOTA : (flags & XFS_DQ_PROJ) ?
+			XFS_PROJ_QUOTA : XFS_GROUP_QUOTA;
 }
 
 STATIC uint
@@ -965,12 +1007,14 @@
 
 	if (uflags & XFS_QUOTA_UDQ_ACCT)
 		flags |= XFS_UQUOTA_ACCT;
+	if (uflags & XFS_QUOTA_PDQ_ACCT)
+		flags |= XFS_PQUOTA_ACCT;
 	if (uflags & XFS_QUOTA_GDQ_ACCT)
 		flags |= XFS_GQUOTA_ACCT;
 	if (uflags & XFS_QUOTA_UDQ_ENFD)
 		flags |= XFS_UQUOTA_ENFD;
-	if (uflags & XFS_QUOTA_GDQ_ENFD)
-		flags |= XFS_GQUOTA_ENFD;
+	if (uflags & (XFS_QUOTA_PDQ_ENFD|XFS_QUOTA_GDQ_ENFD))
+		flags |= XFS_OQUOTA_ENFD;
 	return (flags);
 }
 
@@ -984,12 +1028,16 @@
 	uflags = 0;
 	if (flags & XFS_UQUOTA_ACCT)
 		uflags |= XFS_QUOTA_UDQ_ACCT;
+	if (flags & XFS_PQUOTA_ACCT)
+		uflags |= XFS_QUOTA_PDQ_ACCT;
 	if (flags & XFS_GQUOTA_ACCT)
 		uflags |= XFS_QUOTA_GDQ_ACCT;
 	if (flags & XFS_UQUOTA_ENFD)
 		uflags |= XFS_QUOTA_UDQ_ENFD;
-	if (flags & XFS_GQUOTA_ENFD)
-		uflags |= XFS_QUOTA_GDQ_ENFD;
+	if (flags & (XFS_OQUOTA_ENFD)) {
+		uflags |= (flags & XFS_GQUOTA_ACCT) ?
+			XFS_QUOTA_GDQ_ENFD : XFS_QUOTA_PDQ_ENFD;
+	}
 	return (uflags);
 }
 
@@ -1070,7 +1118,7 @@
 			xfs_qm_dqrele(ip->i_udquot);
 			ip->i_udquot = NULL;
 		}
-		if ((flags & XFS_GQUOTA_ACCT) && ip->i_gdquot) {
+		if (flags & (XFS_PQUOTA_ACCT|XFS_GQUOTA_ACCT) && ip->i_gdquot) {
 			xfs_qm_dqrele(ip->i_gdquot);
 			ip->i_gdquot = NULL;
 		}
@@ -1160,7 +1208,6 @@
 {
 	cmn_err(CE_DEBUG, "-----------DQTEST DQUOT----------------");
 	cmn_err(CE_DEBUG, "---- dquot ID = %d", d->d_id);
-	cmn_err(CE_DEBUG, "---- type     = %s", XFS_QM_ISUDQ(d)? "USR" : "GRP");
 	cmn_err(CE_DEBUG, "---- fs       = 0x%p", d->q_mount);
 	cmn_err(CE_DEBUG, "---- bcount   = %Lu (0x%x)",
 		d->d_bcount, (int)d->d_bcount);
@@ -1231,7 +1278,7 @@
 #ifdef QUOTADEBUG
 	if (!err) {
 		cmn_err(CE_DEBUG, "%d [%s] [0x%p] qchecked",
-			d->d_id, XFS_QM_ISUDQ(d) ? "USR" : "GRP", d->q_mount);
+			d->d_id, DQFLAGTO_TYPESTR(d), d->q_mount);
 	}
 #endif
 	return (err);
@@ -1287,6 +1334,7 @@
 xfs_qm_internalqcheck_get_dquots(
 	xfs_mount_t	*mp,
 	xfs_dqid_t	uid,
+	xfs_dqid_t	projid,
 	xfs_dqid_t	gid,
 	xfs_dqtest_t	**ud,
 	xfs_dqtest_t	**gd)
@@ -1295,6 +1343,8 @@
 		xfs_qm_internalqcheck_dqget(mp, uid, XFS_DQ_USER, ud);
 	if (XFS_IS_GQUOTA_ON(mp))
 		xfs_qm_internalqcheck_dqget(mp, gid, XFS_DQ_GROUP, gd);
+	else if (XFS_IS_PQUOTA_ON(mp))
+		xfs_qm_internalqcheck_dqget(mp, projid, XFS_DQ_PROJ, gd);
 }
 
 
@@ -1362,13 +1412,14 @@
 	}
 	xfs_qm_internalqcheck_get_dquots(mp,
 					(xfs_dqid_t) ip->i_d.di_uid,
+					(xfs_dqid_t) ip->i_d.di_projid,
 					(xfs_dqid_t) ip->i_d.di_gid,
 					&ud, &gd);
 	if (XFS_IS_UQUOTA_ON(mp)) {
 		ASSERT(ud);
 		xfs_qm_internalqcheck_dqadjust(ip, ud);
 	}
-	if (XFS_IS_GQUOTA_ON(mp)) {
+	if (XFS_IS_OQUOTA_ON(mp)) {
 		ASSERT(gd);
 		xfs_qm_internalqcheck_dqadjust(ip, gd);
 	}
diff --git a/fs/xfs/quota/xfs_quota_priv.h b/fs/xfs/quota/xfs_quota_priv.h
index 414b600..bf413e7 100644
--- a/fs/xfs/quota/xfs_quota_priv.h
+++ b/fs/xfs/quota/xfs_quota_priv.h
@@ -56,6 +56,7 @@
 #define XFS_QI_RTBTIMELIMIT(mp) ((mp)->m_quotainfo->qi_rtbtimelimit)
 #define XFS_QI_ITIMELIMIT(mp)	((mp)->m_quotainfo->qi_itimelimit)
 #define XFS_QI_BWARNLIMIT(mp)	((mp)->m_quotainfo->qi_bwarnlimit)
+#define XFS_QI_RTBWARNLIMIT(mp)	((mp)->m_quotainfo->qi_rtbwarnlimit)
 #define XFS_QI_IWARNLIMIT(mp)	((mp)->m_quotainfo->qi_iwarnlimit)
 #define XFS_QI_QOFFLOCK(mp)	((mp)->m_quotainfo->qi_quotaofflock)
 
@@ -102,7 +103,8 @@
 				     (xfs_Gqm->qm_grp_dqhtable + \
 				      XFS_DQ_HASHVAL(mp, id)))
 #define XFS_IS_DQTYPE_ON(mp, type)   (type == XFS_DQ_USER ? \
-				      XFS_IS_UQUOTA_ON(mp):XFS_IS_GQUOTA_ON(mp))
+					XFS_IS_UQUOTA_ON(mp) : \
+					XFS_IS_OQUOTA_ON(mp))
 #define XFS_IS_DQUOT_UNINITIALIZED(dqp) ( \
 	!dqp->q_core.d_blk_hardlimit && \
 	!dqp->q_core.d_blk_softlimit && \
@@ -177,16 +179,11 @@
 	(!((dqp)->q_core.d_id))
 
 #define XFS_PURGE_INODE(ip)		\
-	{				\
-	  vmap_t dqvmap;		\
-	  vnode_t *dqvp;		\
-	  dqvp = XFS_ITOV(ip);		\
-	  VMAP(dqvp, dqvmap);		\
-	  VN_RELE(dqvp);		\
-	}
+	IRELE(ip);
 
 #define DQFLAGTO_TYPESTR(d)	(((d)->dq_flags & XFS_DQ_USER) ? "USR" : \
-				 (((d)->dq_flags & XFS_DQ_GROUP) ? "GRP" : "???"))
+				 (((d)->dq_flags & XFS_DQ_GROUP) ? "GRP" : \
+				 (((d)->dq_flags & XFS_DQ_PROJ) ? "PRJ":"???")))
 #define DQFLAGTO_DIRTYSTR(d)	(XFS_DQ_IS_DIRTY(d) ? "DIRTY" : "NOTDIRTY")
 
 #endif	/* __XFS_QUOTA_PRIV_H__ */
diff --git a/fs/xfs/quota/xfs_trans_dquot.c b/fs/xfs/quota/xfs_trans_dquot.c
index 149b2a1..3b99daf 100644
--- a/fs/xfs/quota/xfs_trans_dquot.c
+++ b/fs/xfs/quota/xfs_trans_dquot.c
@@ -187,7 +187,7 @@
 /*
  * Wrap around mod_dquot to account for both user and group quotas.
  */
-void
+STATIC void
 xfs_trans_mod_dquot_byino(
 	xfs_trans_t	*tp,
 	xfs_inode_t	*ip,
@@ -207,12 +207,10 @@
 	if (tp->t_dqinfo == NULL)
 		xfs_trans_alloc_dqinfo(tp);
 
-	if (XFS_IS_UQUOTA_ON(mp) && ip->i_udquot) {
+	if (XFS_IS_UQUOTA_ON(mp) && ip->i_udquot)
 		(void) xfs_trans_mod_dquot(tp, ip->i_udquot, field, delta);
-	}
-	if (XFS_IS_GQUOTA_ON(mp) && ip->i_gdquot) {
+	if (XFS_IS_OQUOTA_ON(mp) && ip->i_gdquot)
 		(void) xfs_trans_mod_dquot(tp, ip->i_gdquot, field, delta);
-	}
 }
 
 STATIC xfs_dqtrx_t *
@@ -368,7 +366,7 @@
  * Unreserve just the reservations done by this transaction.
  * dquot is still left locked at exit.
  */
-void
+STATIC void
 xfs_trans_apply_dquot_deltas(
 	xfs_trans_t		*tp)
 {
@@ -499,7 +497,7 @@
 			 * Adjust the RT reservation.
 			 */
 			if (qtrx->qt_rtblk_res != 0) {
-				if (qtrx->qt_blk_res != qtrx->qt_blk_res_used) {
+				if (qtrx->qt_rtblk_res != qtrx->qt_rtblk_res_used) {
 					if (qtrx->qt_rtblk_res >
 					    qtrx->qt_rtblk_res_used)
 					       dqp->q_res_rtbcount -= (xfs_qcnt_t)
@@ -532,12 +530,6 @@
 					    (xfs_qcnt_t)qtrx->qt_icount_delta;
 			}
 
-
-#ifdef QUOTADEBUG
-			if (qtrx->qt_rtblk_res != 0)
-				cmn_err(CE_DEBUG, "RT res %d for 0x%p\n",
-					(int) qtrx->qt_rtblk_res, dqp);
-#endif
 			ASSERT(dqp->q_res_bcount >=
 				INT_GET(dqp->q_core.d_bcount, ARCH_CONVERT));
 			ASSERT(dqp->q_res_icount >=
@@ -638,7 +630,10 @@
 	int		error;
 	xfs_qcnt_t	hardlimit;
 	xfs_qcnt_t	softlimit;
-	time_t		btimer;
+	time_t		timer;
+	xfs_qwarncnt_t	warns;
+	xfs_qwarncnt_t	warnlimit;
+	xfs_qcnt_t	count;
 	xfs_qcnt_t	*resbcountp;
 	xfs_quotainfo_t	*q = mp->m_quotainfo;
 
@@ -653,7 +648,9 @@
 		softlimit = INT_GET(dqp->q_core.d_blk_softlimit, ARCH_CONVERT);
 		if (!softlimit)
 			softlimit = q->qi_bsoftlimit;
-		btimer = INT_GET(dqp->q_core.d_btimer, ARCH_CONVERT);
+		timer = INT_GET(dqp->q_core.d_btimer, ARCH_CONVERT);
+		warns = INT_GET(dqp->q_core.d_bwarns, ARCH_CONVERT);
+		warnlimit = XFS_QI_BWARNLIMIT(dqp->q_mount);
 		resbcountp = &dqp->q_res_bcount;
 	} else {
 		ASSERT(flags & XFS_TRANS_DQ_RES_RTBLKS);
@@ -663,7 +660,9 @@
 		softlimit = INT_GET(dqp->q_core.d_rtb_softlimit, ARCH_CONVERT);
 		if (!softlimit)
 			softlimit = q->qi_rtbsoftlimit;
-		btimer = INT_GET(dqp->q_core.d_rtbtimer, ARCH_CONVERT);
+		timer = INT_GET(dqp->q_core.d_rtbtimer, ARCH_CONVERT);
+		warns = INT_GET(dqp->q_core.d_rtbwarns, ARCH_CONVERT);
+		warnlimit = XFS_QI_RTBWARNLIMIT(dqp->q_mount);
 		resbcountp = &dqp->q_res_rtbcount;
 	}
 	error = 0;
@@ -693,37 +692,36 @@
 				 * If timer or warnings has expired,
 				 * return EDQUOT
 				 */
-				if ((btimer != 0 && get_seconds() > btimer) ||
-				    (dqp->q_core.d_bwarns &&
-				     INT_GET(dqp->q_core.d_bwarns, ARCH_CONVERT) >=
-				     XFS_QI_BWARNLIMIT(dqp->q_mount))) {
+				if ((timer != 0 && get_seconds() > timer) ||
+				    (warns != 0 && warns >= warnlimit)) {
 					error = EDQUOT;
 					goto error_return;
 				}
 			}
 		}
 		if (ninos > 0) {
-			hardlimit = INT_GET(dqp->q_core.d_ino_hardlimit, ARCH_CONVERT);
+			count = INT_GET(dqp->q_core.d_icount, ARCH_CONVERT);
+			timer = INT_GET(dqp->q_core.d_itimer, ARCH_CONVERT);
+			warns = INT_GET(dqp->q_core.d_iwarns, ARCH_CONVERT);
+			warnlimit = XFS_QI_IWARNLIMIT(dqp->q_mount);
+			hardlimit = INT_GET(dqp->q_core.d_ino_hardlimit,
+						ARCH_CONVERT);
 			if (!hardlimit)
 				hardlimit = q->qi_ihardlimit;
-			softlimit = INT_GET(dqp->q_core.d_ino_softlimit, ARCH_CONVERT);
+			softlimit = INT_GET(dqp->q_core.d_ino_softlimit,
+						ARCH_CONVERT);
 			if (!softlimit)
 				softlimit = q->qi_isoftlimit;
-			if (hardlimit > 0ULL &&
-			    INT_GET(dqp->q_core.d_icount, ARCH_CONVERT) >= hardlimit) {
+			if (hardlimit > 0ULL && count >= hardlimit) {
 				error = EDQUOT;
 				goto error_return;
-			} else if (softlimit > 0ULL &&
-				   INT_GET(dqp->q_core.d_icount, ARCH_CONVERT) >= softlimit) {
+			} else if (softlimit > 0ULL && count >= softlimit) {
 				/*
 				 * If timer or warnings has expired,
 				 * return EDQUOT
 				 */
-				if ((dqp->q_core.d_itimer &&
-				     get_seconds() > INT_GET(dqp->q_core.d_itimer, ARCH_CONVERT)) ||
-				    (dqp->q_core.d_iwarns &&
-				     INT_GET(dqp->q_core.d_iwarns, ARCH_CONVERT) >=
-				     XFS_QI_IWARNLIMIT(dqp->q_mount))) {
+				if ((timer != 0 && get_seconds() > timer) ||
+				     (warns != 0 && warns >= warnlimit)) {
 					error = EDQUOT;
 					goto error_return;
 				}
diff --git a/fs/xfs/support/debug.c b/fs/xfs/support/debug.c
index 7d6e1f3..4ed7b69 100644
--- a/fs/xfs/support/debug.c
+++ b/fs/xfs/support/debug.c
@@ -36,7 +36,6 @@
 #include <linux/sched.h>
 #include <linux/kernel.h>
 
-int			doass = 1;
 static char		message[256];	/* keep it off the stack */
 static DEFINE_SPINLOCK(xfs_err_lock);
 
diff --git a/fs/xfs/support/debug.h b/fs/xfs/support/debug.h
index 40b0f4c..c5b9365 100644
--- a/fs/xfs/support/debug.h
+++ b/fs/xfs/support/debug.h
@@ -50,16 +50,11 @@
 #endif
 
 #ifdef DEBUG
-# ifdef lint
-#  define ASSERT(EX)	((void)0) /* avoid "constant in conditional" babble */
-# else
-#  define ASSERT(EX) ((!doass||(EX))?((void)0):assfail(#EX, __FILE__, __LINE__))
-# endif	/* lint */
+# define ASSERT(EX)	((EX) ? ((void)0) : assfail(#EX, __FILE__, __LINE__))
 #else
 # define ASSERT(x)	((void)0)
 #endif
 
-extern int doass;		/* dynamically turn off asserts */
 extern void assfail(char *, char *, int);
 #ifdef DEBUG
 extern unsigned long random(void);
diff --git a/fs/xfs/xfs_alloc.c b/fs/xfs/xfs_alloc.c
index 36603db..dcfe197 100644
--- a/fs/xfs/xfs_alloc.c
+++ b/fs/xfs/xfs_alloc.c
@@ -59,7 +59,7 @@
 #define	XFSA_FIXUP_BNO_OK	1
 #define	XFSA_FIXUP_CNT_OK	2
 
-int
+STATIC int
 xfs_alloc_search_busy(xfs_trans_t *tp,
 		    xfs_agnumber_t agno,
 		    xfs_agblock_t bno,
@@ -2562,7 +2562,7 @@
 /*
  * returns non-zero if any of (agno,bno):len is in a busy list
  */
-int
+STATIC int
 xfs_alloc_search_busy(xfs_trans_t *tp,
 		    xfs_agnumber_t agno,
 		    xfs_agblock_t bno,
diff --git a/fs/xfs/xfs_attr.c b/fs/xfs/xfs_attr.c
index ee8b590..a41ad3a 100644
--- a/fs/xfs/xfs_attr.c
+++ b/fs/xfs/xfs_attr.c
@@ -71,6 +71,11 @@
  * Provide the external interfaces to manage attribute lists.
  */
 
+#define ATTR_SYSCOUNT	2
+STATIC struct attrnames posix_acl_access;
+STATIC struct attrnames posix_acl_default;
+STATIC struct attrnames *attr_system_names[ATTR_SYSCOUNT];
+
 /*========================================================================
  * Function prototypes for the kernel.
  *========================================================================*/
@@ -83,6 +88,7 @@
 /*
  * Internal routines when attribute list is one block.
  */
+STATIC int xfs_attr_leaf_get(xfs_da_args_t *args);
 STATIC int xfs_attr_leaf_addname(xfs_da_args_t *args);
 STATIC int xfs_attr_leaf_removename(xfs_da_args_t *args);
 STATIC int xfs_attr_leaf_list(xfs_attr_list_context_t *context);
@@ -90,6 +96,7 @@
 /*
  * Internal routines when attribute list is more than one block.
  */
+STATIC int xfs_attr_node_get(xfs_da_args_t *args);
 STATIC int xfs_attr_node_addname(xfs_da_args_t *args);
 STATIC int xfs_attr_node_removename(xfs_da_args_t *args);
 STATIC int xfs_attr_node_list(xfs_attr_list_context_t *context);
@@ -1102,7 +1109,7 @@
  * This leaf block cannot have a "remote" value, we only call this routine
  * if bmap_one_block() says there is only one block (ie: no remote blks).
  */
-int
+STATIC int
 xfs_attr_leaf_get(xfs_da_args_t *args)
 {
 	xfs_dabuf_t *bp;
@@ -1707,7 +1714,7 @@
  * block, ie: both true Btree attr lists and for single-leaf-blocks with
  * "remote" values taking up more blocks.
  */
-int
+STATIC int
 xfs_attr_node_get(xfs_da_args_t *args)
 {
 	xfs_da_state_t *state;
@@ -2398,7 +2405,7 @@
 	return xfs_acl_vhasacl_default(vp);
 }
 
-struct attrnames posix_acl_access = {
+STATIC struct attrnames posix_acl_access = {
 	.attr_name	= "posix_acl_access",
 	.attr_namelen	= sizeof("posix_acl_access") - 1,
 	.attr_get	= posix_acl_access_get,
@@ -2407,7 +2414,7 @@
 	.attr_exists	= posix_acl_access_exists,
 };
 
-struct attrnames posix_acl_default = {
+STATIC struct attrnames posix_acl_default = {
 	.attr_name	= "posix_acl_default",
 	.attr_namelen	= sizeof("posix_acl_default") - 1,
 	.attr_get	= posix_acl_default_get,
@@ -2416,7 +2423,7 @@
 	.attr_exists	= posix_acl_default_exists,
 };
 
-struct attrnames *attr_system_names[] =
+STATIC struct attrnames *attr_system_names[] =
 	{ &posix_acl_access, &posix_acl_default };
 
 
diff --git a/fs/xfs/xfs_attr.h b/fs/xfs/xfs_attr.h
index 67cd0f5..45ab1c5 100644
--- a/fs/xfs/xfs_attr.h
+++ b/fs/xfs/xfs_attr.h
@@ -76,11 +76,6 @@
 extern struct attrnames attr_trusted;
 extern struct attrnames *attr_namespaces[ATTR_NAMECOUNT];
 
-#define ATTR_SYSCOUNT	2
-extern struct attrnames posix_acl_access;
-extern struct attrnames posix_acl_default;
-extern struct attrnames *attr_system_names[ATTR_SYSCOUNT];
-
 extern attrnames_t *attr_lookup_namespace(char *, attrnames_t **, int);
 extern int attr_generic_list(struct vnode *, void *, size_t, int, ssize_t *);
 
@@ -184,8 +179,6 @@
 			 struct attrlist_cursor_kern *, struct cred *);
 int xfs_attr_inactive(struct xfs_inode *dp);
 
-int xfs_attr_node_get(struct xfs_da_args *);
-int xfs_attr_leaf_get(struct xfs_da_args *);
 int xfs_attr_shortform_getvalue(struct xfs_da_args *);
 int xfs_attr_fetch(struct xfs_inode *, char *, int,
 			char *, int *, int, struct cred *);
diff --git a/fs/xfs/xfs_attr_leaf.c b/fs/xfs/xfs_attr_leaf.c
index b11256e..1cdd574 100644
--- a/fs/xfs/xfs_attr_leaf.c
+++ b/fs/xfs/xfs_attr_leaf.c
@@ -79,6 +79,8 @@
 /*
  * Routines used for growing the Btree.
  */
+STATIC int xfs_attr_leaf_create(xfs_da_args_t *args, xfs_dablk_t which_block,
+				    xfs_dabuf_t **bpp);
 STATIC int xfs_attr_leaf_add_work(xfs_dabuf_t *leaf_buffer, xfs_da_args_t *args,
 					      int freemap_index);
 STATIC void xfs_attr_leaf_compact(xfs_trans_t *trans, xfs_dabuf_t *leaf_buffer);
@@ -92,6 +94,16 @@
 					   int *number_usedbytes_in_blk1);
 
 /*
+ * Routines used for shrinking the Btree.
+ */
+STATIC int xfs_attr_node_inactive(xfs_trans_t **trans, xfs_inode_t *dp,
+				  xfs_dabuf_t *bp, int level);
+STATIC int xfs_attr_leaf_inactive(xfs_trans_t **trans, xfs_inode_t *dp,
+				  xfs_dabuf_t *bp);
+STATIC int xfs_attr_leaf_freextent(xfs_trans_t **trans, xfs_inode_t *dp,
+				   xfs_dablk_t blkno, int blkcnt);
+
+/*
  * Utility routines.
  */
 STATIC void xfs_attr_leaf_moveents(xfs_attr_leafblock_t *src_leaf,
@@ -99,6 +111,10 @@
 					 xfs_attr_leafblock_t *dst_leaf,
 					 int dst_start, int move_count,
 					 xfs_mount_t *mp);
+STATIC int xfs_attr_leaf_entsize(xfs_attr_leafblock_t *leaf, int index);
+STATIC int xfs_attr_put_listent(xfs_attr_list_context_t *context,
+			     attrnames_t *, char *name, int namelen,
+			     int valuelen);
 
 
 /*========================================================================
@@ -774,7 +790,7 @@
  * Create the initial contents of a leaf attribute list
  * or a leaf in a node attribute list.
  */
-int
+STATIC int
 xfs_attr_leaf_create(xfs_da_args_t *args, xfs_dablk_t blkno, xfs_dabuf_t **bpp)
 {
 	xfs_attr_leafblock_t *leaf;
@@ -2209,7 +2225,7 @@
  * Calculate the number of bytes used to store the indicated attribute
  * (whether local or remote only calculate bytes in this block).
  */
-int
+STATIC int
 xfs_attr_leaf_entsize(xfs_attr_leafblock_t *leaf, int index)
 {
 	xfs_attr_leaf_name_local_t *name_loc;
@@ -2380,7 +2396,7 @@
  * we may be reading them directly out of a user buffer.
  */
 /*ARGSUSED*/
-int
+STATIC int
 xfs_attr_put_listent(xfs_attr_list_context_t *context,
 		     attrnames_t *namesp, char *name, int namelen, int valuelen)
 {
@@ -2740,7 +2756,7 @@
  * Recurse (gasp!) through the attribute nodes until we find leaves.
  * We're doing a depth-first traversal in order to invalidate everything.
  */
-int
+STATIC int
 xfs_attr_node_inactive(xfs_trans_t **trans, xfs_inode_t *dp, xfs_dabuf_t *bp,
 				   int level)
 {
@@ -2849,7 +2865,7 @@
  * Note that we must release the lock on the buffer so that we are not
  * caught holding something that the logging code wants to flush to disk.
  */
-int
+STATIC int
 xfs_attr_leaf_inactive(xfs_trans_t **trans, xfs_inode_t *dp, xfs_dabuf_t *bp)
 {
 	xfs_attr_leafblock_t *leaf;
@@ -2934,7 +2950,7 @@
  * Look at all the extents for this logical region,
  * invalidate any buffers that are incore/in transactions.
  */
-int
+STATIC int
 xfs_attr_leaf_freextent(xfs_trans_t **trans, xfs_inode_t *dp,
 				    xfs_dablk_t blkno, int blkcnt)
 {
diff --git a/fs/xfs/xfs_attr_leaf.h b/fs/xfs/xfs_attr_leaf.h
index b1480e0..0a4cfad 100644
--- a/fs/xfs/xfs_attr_leaf.h
+++ b/fs/xfs/xfs_attr_leaf.h
@@ -261,8 +261,6 @@
 /*
  * Routines used for growing the Btree.
  */
-int	xfs_attr_leaf_create(struct xfs_da_args *args, xfs_dablk_t which_block,
-				    struct xfs_dabuf **bpp);
 int	xfs_attr_leaf_split(struct xfs_da_state *state,
 				   struct xfs_da_state_blk *oldblk,
 				   struct xfs_da_state_blk *newblk);
@@ -284,12 +282,6 @@
 				       struct xfs_da_state_blk *drop_blk,
 				       struct xfs_da_state_blk *save_blk);
 int	xfs_attr_root_inactive(struct xfs_trans **trans, struct xfs_inode *dp);
-int	xfs_attr_node_inactive(struct xfs_trans **trans, struct xfs_inode *dp,
-				      struct xfs_dabuf *bp, int level);
-int	xfs_attr_leaf_inactive(struct xfs_trans **trans, struct xfs_inode *dp,
-				      struct xfs_dabuf *bp);
-int	xfs_attr_leaf_freextent(struct xfs_trans **trans, struct xfs_inode *dp,
-				       xfs_dablk_t blkno, int blkcnt);
 
 /*
  * Utility routines.
@@ -299,10 +291,6 @@
 				   struct xfs_dabuf *leaf2_bp);
 int	xfs_attr_leaf_newentsize(struct xfs_da_args *args, int blocksize,
 					int *local);
-int	xfs_attr_leaf_entsize(struct xfs_attr_leafblock *leaf, int index);
-int	xfs_attr_put_listent(struct xfs_attr_list_context *context,
-			     struct attrnames *, char *name, int namelen,
-			     int valuelen);
 int	xfs_attr_rolltrans(struct xfs_trans **transp, struct xfs_inode *dp);
 
 #endif	/* __XFS_ATTR_LEAF_H__ */
diff --git a/fs/xfs/xfs_bit.c b/fs/xfs/xfs_bit.c
index a20a6c3..76c9ad3 100644
--- a/fs/xfs/xfs_bit.c
+++ b/fs/xfs/xfs_bit.c
@@ -45,7 +45,7 @@
 /*
  * Index of high bit number in byte, -1 for none set, 0..7 otherwise.
  */
-const char xfs_highbit[256] = {
+STATIC const char xfs_highbit[256] = {
        -1, 0, 1, 1, 2, 2, 2, 2,			/* 00 .. 07 */
 	3, 3, 3, 3, 3, 3, 3, 3,			/* 08 .. 0f */
 	4, 4, 4, 4, 4, 4, 4, 4,			/* 10 .. 17 */
diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c
index de31624..6f5d283 100644
--- a/fs/xfs/xfs_bmap.c
+++ b/fs/xfs/xfs_bmap.c
@@ -301,6 +301,19 @@
 	xfs_bmbt_irec_t	*gotp,		/* out: extent entry found */
 	xfs_bmbt_irec_t	*prevp);	/* out: previous extent entry found */
 
+/*
+ * Check the last inode extent to determine whether this allocation will result
+ * in blocks being allocated at the end of the file. When we allocate new data
+ * blocks at the end of the file which do not start at the previous data block,
+ * we will try to align the new blocks at stripe unit boundaries.
+ */
+STATIC int				/* error */
+xfs_bmap_isaeof(
+	xfs_inode_t	*ip,		/* incore inode pointer */
+	xfs_fileoff_t   off,		/* file offset in fsblocks */
+	int             whichfork,	/* data or attribute fork */
+	char		*aeof);		/* return value */
+
 #ifdef XFS_BMAP_TRACE
 /*
  * Add a bmap trace buffer entry.  Base routine for the others.
@@ -4532,18 +4545,17 @@
 	xfs_extlen_t	alen;		/* allocated extent length */
 	xfs_fileoff_t	aoff;		/* allocated file offset */
 	xfs_bmalloca_t	bma;		/* args for xfs_bmap_alloc */
-	char		contig;		/* allocation must be one extent */
 	xfs_btree_cur_t	*cur;		/* bmap btree cursor */
-	char		delay;		/* this request is for delayed alloc */
 	xfs_fileoff_t	end;		/* end of mapped file region */
 	int		eof;		/* we've hit the end of extent list */
+	char		contig;		/* allocation must be one extent */
+	char		delay;		/* this request is for delayed alloc */
+	char		exact;		/* don't do all of wasdelayed extent */
 	xfs_bmbt_rec_t	*ep;		/* extent list entry pointer */
 	int		error;		/* error return */
-	char		exact;		/* don't do all of wasdelayed extent */
 	xfs_bmbt_irec_t	got;		/* current extent list record */
 	xfs_ifork_t	*ifp;		/* inode fork pointer */
 	xfs_extlen_t	indlen;		/* indirect blocks length */
-	char		inhole;		/* current location is hole in file */
 	xfs_extnum_t	lastx;		/* last useful extent number */
 	int		logflags;	/* flags for transaction logging */
 	xfs_extlen_t	minleft;	/* min blocks left after allocation */
@@ -4554,13 +4566,15 @@
 	xfs_extnum_t	nextents;	/* number of extents in file */
 	xfs_fileoff_t	obno;		/* old block number (offset) */
 	xfs_bmbt_irec_t	prev;		/* previous extent list record */
-	char		stateless;	/* ignore state flag set */
 	int		tmp_logflags;	/* temp flags holder */
+	int		whichfork;	/* data or attr fork */
+	char		inhole;		/* current location is hole in file */
+	char		stateless;	/* ignore state flag set */
 	char		trim;		/* output trimmed to match range */
 	char		userdata;	/* allocating non-metadata */
 	char		wasdelay;	/* old extent was delayed */
-	int		whichfork;	/* data or attr fork */
 	char		wr;		/* this is a write request */
+	char		rt;		/* this is a realtime file */
 	char		rsvd;		/* OK to allocate reserved blocks */
 #ifdef DEBUG
 	xfs_fileoff_t	orig_bno;	/* original block number value */
@@ -4590,6 +4604,7 @@
 	}
 	if (XFS_FORCED_SHUTDOWN(mp))
 		return XFS_ERROR(EIO);
+	rt = XFS_IS_REALTIME_INODE(ip);
 	ifp = XFS_IFORK_PTR(ip, whichfork);
 	ASSERT(ifp->if_ext_max ==
 	       XFS_IFORK_SIZE(ip, whichfork) / (uint)sizeof(xfs_bmbt_rec_t));
@@ -4694,9 +4709,16 @@
 			}
 			minlen = contig ? alen : 1;
 			if (delay) {
-				indlen = (xfs_extlen_t)
-					xfs_bmap_worst_indlen(ip, alen);
-				ASSERT(indlen > 0);
+				xfs_extlen_t	extsz = 0;
+
+				/* Figure out the extent size, adjust alen */
+				if (rt) {
+					if (!(extsz = ip->i_d.di_extsize))
+						extsz = mp->m_sb.sb_rextsize;
+					alen = roundup(alen, extsz);
+					extsz = alen / mp->m_sb.sb_rextsize;
+				}
+
 				/*
 				 * Make a transaction-less quota reservation for
 				 * delayed allocation blocks. This number gets
@@ -4704,8 +4726,10 @@
 				 * We return EDQUOT if we haven't allocated
 				 * blks already inside this loop;
 				 */
-				if (XFS_TRANS_RESERVE_BLKQUOTA(
-						mp, NULL, ip, (long)alen)) {
+				if (XFS_TRANS_RESERVE_QUOTA_NBLKS(
+						mp, NULL, ip, (long)alen, 0,
+						rt ? XFS_QMOPT_RES_RTBLKS :
+						     XFS_QMOPT_RES_REGBLKS)) {
 					if (n == 0) {
 						*nmap = 0;
 						ASSERT(cur == NULL);
@@ -4718,40 +4742,34 @@
 				 * Split changing sb for alen and indlen since
 				 * they could be coming from different places.
 				 */
-				if (ip->i_d.di_flags & XFS_DIFLAG_REALTIME) {
-					xfs_extlen_t	extsz;
-					xfs_extlen_t	ralen;
-					if (!(extsz = ip->i_d.di_extsize))
-						extsz = mp->m_sb.sb_rextsize;
-					ralen = roundup(alen, extsz);
-					ralen = ralen / mp->m_sb.sb_rextsize;
-					if (xfs_mod_incore_sb(mp,
-						XFS_SBS_FREXTENTS,
-						-(ralen), rsvd)) {
-						if (XFS_IS_QUOTA_ON(ip->i_mount))
-							XFS_TRANS_UNRESERVE_BLKQUOTA(
-						     		mp, NULL, ip,
-								(long)alen);
-						break;
-					}
-				} else {
-					if (xfs_mod_incore_sb(mp,
-							      XFS_SBS_FDBLOCKS,
-							      -(alen), rsvd)) {
-						if (XFS_IS_QUOTA_ON(ip->i_mount))
-							XFS_TRANS_UNRESERVE_BLKQUOTA(
-								mp, NULL, ip,
-								(long)alen);
-						break;
-					}
-				}
+				indlen = (xfs_extlen_t)
+					xfs_bmap_worst_indlen(ip, alen);
+				ASSERT(indlen > 0);
 
-				if (xfs_mod_incore_sb(mp, XFS_SBS_FDBLOCKS,
-						-(indlen), rsvd)) {
-					XFS_TRANS_UNRESERVE_BLKQUOTA(
-						mp, NULL, ip, (long)alen);
+				if (rt)
+					error = xfs_mod_incore_sb(mp,
+							XFS_SBS_FREXTENTS,
+							-(extsz), rsvd);
+				else
+					error = xfs_mod_incore_sb(mp,
+							XFS_SBS_FDBLOCKS,
+							-(alen), rsvd);
+				if (!error)
+					error = xfs_mod_incore_sb(mp,
+							XFS_SBS_FDBLOCKS,
+							-(indlen), rsvd);
+
+				if (error) {
+					if (XFS_IS_QUOTA_ON(ip->i_mount))
+						/* unreserve the blocks now */
+						XFS_TRANS_UNRESERVE_QUOTA_NBLKS(
+							mp, NULL, ip,
+							(long)alen, 0, rt ?
+							XFS_QMOPT_RES_RTBLKS :
+							XFS_QMOPT_RES_REGBLKS);
 					break;
 				}
+
 				ip->i_delayed_blks += alen;
 				abno = NULLSTARTBLOCK(indlen);
 			} else {
@@ -5376,13 +5394,24 @@
 		}
 		if (wasdel) {
 			ASSERT(STARTBLOCKVAL(del.br_startblock) > 0);
-			xfs_mod_incore_sb(mp, XFS_SBS_FDBLOCKS,
-				(int)del.br_blockcount, rsvd);
-			/* Unreserve our quota space */
-			XFS_TRANS_RESERVE_QUOTA_NBLKS(
-				mp, NULL, ip, -((long)del.br_blockcount), 0,
-				isrt ?	XFS_QMOPT_RES_RTBLKS :
+			/* Update realtim/data freespace, unreserve quota */
+			if (isrt) {
+				xfs_filblks_t rtexts;
+
+				rtexts = XFS_FSB_TO_B(mp, del.br_blockcount);
+				do_div(rtexts, mp->m_sb.sb_rextsize);
+				xfs_mod_incore_sb(mp, XFS_SBS_FREXTENTS,
+						(int)rtexts, rsvd);
+				XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, NULL, ip,
+					-((long)del.br_blockcount), 0,
+					XFS_QMOPT_RES_RTBLKS);
+			} else {
+				xfs_mod_incore_sb(mp, XFS_SBS_FDBLOCKS,
+						(int)del.br_blockcount, rsvd);
+				XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, NULL, ip,
+					-((long)del.br_blockcount), 0,
 					XFS_QMOPT_RES_REGBLKS);
+			}
 			ip->i_delayed_blks -= del.br_blockcount;
 			if (cur)
 				cur->bc_private.b.flags |=
@@ -5714,7 +5743,7 @@
  * blocks at the end of the file which do not start at the previous data block,
  * we will try to align the new blocks at stripe unit boundaries.
  */
-int					/* error */
+STATIC int				/* error */
 xfs_bmap_isaeof(
 	xfs_inode_t	*ip,		/* incore inode pointer */
 	xfs_fileoff_t   off,		/* file offset in fsblocks */
diff --git a/fs/xfs/xfs_bmap.h b/fs/xfs/xfs_bmap.h
index f1bc22f..e6d22ec 100644
--- a/fs/xfs/xfs_bmap.h
+++ b/fs/xfs/xfs_bmap.h
@@ -332,19 +332,6 @@
 	int			iflags);	/* interface flags */
 
 /*
- * Check the last inode extent to determine whether this allocation will result
- * in blocks being allocated at the end of the file. When we allocate new data
- * blocks at the end of the file which do not start at the previous data block,
- * we will try to align the new blocks at stripe unit boundaries.
- */
-int
-xfs_bmap_isaeof(
-	struct xfs_inode	*ip,
-	xfs_fileoff_t		off,
-	int			whichfork,
-	char			*aeof);
-
-/*
  * Check if the endoff is outside the last extent. If so the caller will grow
  * the allocation to a stripe unit boundary
  */
diff --git a/fs/xfs/xfs_bmap_btree.c b/fs/xfs/xfs_bmap_btree.c
index 163305a..09c4135 100644
--- a/fs/xfs/xfs_bmap_btree.c
+++ b/fs/xfs/xfs_bmap_btree.c
@@ -2331,20 +2331,6 @@
 	return xfs_bmbt_lookup(cur, XFS_LOOKUP_GE, stat);
 }
 
-int					/* error */
-xfs_bmbt_lookup_le(
-	xfs_btree_cur_t	*cur,
-	xfs_fileoff_t	off,
-	xfs_fsblock_t	bno,
-	xfs_filblks_t	len,
-	int		*stat)		/* success/failure */
-{
-	cur->bc_rec.b.br_startoff = off;
-	cur->bc_rec.b.br_startblock = bno;
-	cur->bc_rec.b.br_blockcount = len;
-	return xfs_bmbt_lookup(cur, XFS_LOOKUP_LE, stat);
-}
-
 /*
  * Give the bmap btree a new root block.  Copy the old broot contents
  * down into a real block and make the broot point to it.
diff --git a/fs/xfs/xfs_bmap_btree.h b/fs/xfs/xfs_bmap_btree.h
index 843ff12..0a40cf1 100644
--- a/fs/xfs/xfs_bmap_btree.h
+++ b/fs/xfs/xfs_bmap_btree.h
@@ -580,14 +580,6 @@
 	xfs_filblks_t,
 	int *);
 
-int
-xfs_bmbt_lookup_le(
-	struct xfs_btree_cur *,
-	xfs_fileoff_t,
-	xfs_fsblock_t,
-	xfs_filblks_t,
-	int *);
-
 /*
  * Give the bmap btree a new root block.  Copy the old broot contents
  * down into a real block and make the broot point to it.
diff --git a/fs/xfs/xfs_btree.c b/fs/xfs/xfs_btree.c
index 9dd22dd..0cc63d6 100644
--- a/fs/xfs/xfs_btree.c
+++ b/fs/xfs/xfs_btree.c
@@ -90,6 +90,16 @@
  */
 
 /*
+ * Retrieve the block pointer from the cursor at the given level.
+ * This may be a bmap btree root or from a buffer.
+ */
+STATIC xfs_btree_block_t *			/* generic btree block pointer */
+xfs_btree_get_block(
+	xfs_btree_cur_t		*cur,	/* btree cursor */
+	int			level,	/* level in btree */
+	struct xfs_buf		**bpp);	/* buffer containing the block */
+
+/*
  * Checking routine: return maxrecs for the block.
  */
 STATIC int				/* number of records fitting in block */
@@ -497,7 +507,7 @@
  * Retrieve the block pointer from the cursor at the given level.
  * This may be a bmap btree root or from a buffer.
  */
-xfs_btree_block_t *			/* generic btree block pointer */
+STATIC xfs_btree_block_t *		/* generic btree block pointer */
 xfs_btree_get_block(
 	xfs_btree_cur_t		*cur,	/* btree cursor */
 	int			level,	/* level in btree */
diff --git a/fs/xfs/xfs_btree.h b/fs/xfs/xfs_btree.h
index 93872bb..09b4e15 100644
--- a/fs/xfs/xfs_btree.h
+++ b/fs/xfs/xfs_btree.h
@@ -325,16 +325,6 @@
 	int			level);	/* level to change */
 
 /*
- * Retrieve the block pointer from the cursor at the given level.
- * This may be a bmap btree root or from a buffer.
- */
-xfs_btree_block_t *			/* generic btree block pointer */
-xfs_btree_get_block(
-	xfs_btree_cur_t		*cur,	/* btree cursor */
-	int			level,	/* level in btree */
-	struct xfs_buf		**bpp);	/* buffer containing the block */
-
-/*
  * Get a buffer for the block, return it with no data read.
  * Long-form addressing.
  */
diff --git a/fs/xfs/xfs_buf_item.c b/fs/xfs/xfs_buf_item.c
index 9ab0039..30b8285 100644
--- a/fs/xfs/xfs_buf_item.c
+++ b/fs/xfs/xfs_buf_item.c
@@ -172,7 +172,7 @@
  *
  * If the XFS_BLI_STALE flag has been set, then log nothing.
  */
-uint
+STATIC uint
 xfs_buf_item_size(
 	xfs_buf_log_item_t	*bip)
 {
@@ -240,7 +240,7 @@
  * format structure, and the rest point to contiguous chunks
  * within the buffer.
  */
-void
+STATIC void
 xfs_buf_item_format(
 	xfs_buf_log_item_t	*bip,
 	xfs_log_iovec_t		*log_vector)
@@ -365,7 +365,7 @@
  * item in memory so it cannot be written out.  Simply call bpin()
  * on the buffer to do this.
  */
-void
+STATIC void
 xfs_buf_item_pin(
 	xfs_buf_log_item_t	*bip)
 {
@@ -391,7 +391,7 @@
  * If the XFS_BLI_STALE flag is set and we are the last reference,
  * then free up the buf log item and unlock the buffer.
  */
-void
+STATIC void
 xfs_buf_item_unpin(
 	xfs_buf_log_item_t	*bip,
 	int			stale)
@@ -446,7 +446,7 @@
  * so we need to free the item's descriptor (that points to the item)
  * in the transaction.
  */
-void
+STATIC void
 xfs_buf_item_unpin_remove(
 	xfs_buf_log_item_t	*bip,
 	xfs_trans_t		*tp)
@@ -493,7 +493,7 @@
  * the lock right away, return 0.  If we can get the lock, pull the
  * buffer from the free list, mark it busy, and return 1.
  */
-uint
+STATIC uint
 xfs_buf_item_trylock(
 	xfs_buf_log_item_t	*bip)
 {
@@ -537,7 +537,7 @@
  * This is for support of xfs_trans_bhold(). Make sure the
  * XFS_BLI_HOLD field is cleared if we don't free the item.
  */
-void
+STATIC void
 xfs_buf_item_unlock(
 	xfs_buf_log_item_t	*bip)
 {
@@ -635,7 +635,7 @@
  * by returning the original lsn of that transaction here rather than
  * the current one.
  */
-xfs_lsn_t
+STATIC xfs_lsn_t
 xfs_buf_item_committed(
 	xfs_buf_log_item_t	*bip,
 	xfs_lsn_t		lsn)
@@ -654,7 +654,7 @@
  * and have aborted this transaction, we'll trap this buffer when it tries to
  * get written out.
  */
-void
+STATIC void
 xfs_buf_item_abort(
 	xfs_buf_log_item_t	*bip)
 {
@@ -674,7 +674,7 @@
  * B_DELWRI set, then get it going out to disk with a call to bawrite().
  * If not, then just release the buffer.
  */
-void
+STATIC void
 xfs_buf_item_push(
 	xfs_buf_log_item_t	*bip)
 {
@@ -693,7 +693,7 @@
 }
 
 /* ARGSUSED */
-void
+STATIC void
 xfs_buf_item_committing(xfs_buf_log_item_t *bip, xfs_lsn_t commit_lsn)
 {
 }
@@ -701,7 +701,7 @@
 /*
  * This is the ops vector shared by all buf log items.
  */
-struct xfs_item_ops xfs_buf_item_ops = {
+STATIC struct xfs_item_ops xfs_buf_item_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_buf_item_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_buf_item_format,
diff --git a/fs/xfs/xfs_buf_item.h b/fs/xfs/xfs_buf_item.h
index 5f1b0c9..01aed5f 100644
--- a/fs/xfs/xfs_buf_item.h
+++ b/fs/xfs/xfs_buf_item.h
@@ -80,7 +80,7 @@
  * user or group dquots and may require special recovery handling.
  */
 #define	XFS_BLI_UDQUOT_BUF	0x4
-/* #define XFS_BLI_PDQUOT_BUF	0x8 */
+#define XFS_BLI_PDQUOT_BUF	0x8
 #define	XFS_BLI_GDQUOT_BUF	0x10
 
 #define	XFS_BLI_CHUNK		128
diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c
index d7fe288..8b792dd 100644
--- a/fs/xfs/xfs_da_btree.c
+++ b/fs/xfs/xfs_da_btree.c
@@ -113,7 +113,10 @@
 STATIC uint	xfs_da_node_lasthash(xfs_dabuf_t *bp, int *count);
 STATIC int	xfs_da_node_order(xfs_dabuf_t *node1_bp, xfs_dabuf_t *node2_bp);
 STATIC xfs_dabuf_t *xfs_da_buf_make(int nbuf, xfs_buf_t **bps, inst_t *ra);
-
+STATIC int	xfs_da_blk_unlink(xfs_da_state_t *state,
+				  xfs_da_state_blk_t *drop_blk,
+				  xfs_da_state_blk_t *save_blk);
+STATIC void	xfs_da_state_kill_altpath(xfs_da_state_t *state);
 
 /*========================================================================
  * Routines used for growing the Btree.
@@ -1424,7 +1427,7 @@
 /*
  * Unlink a block from a doubly linked list of blocks.
  */
-int							/* error */
+STATIC int						/* error */
 xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk,
 				 xfs_da_state_blk_t *save_blk)
 {
@@ -2381,7 +2384,7 @@
 /*
  * Kill the altpath contents of a da-state structure.
  */
-void
+STATIC void
 xfs_da_state_kill_altpath(xfs_da_state_t *state)
 {
 	int	i;
diff --git a/fs/xfs/xfs_da_btree.h b/fs/xfs/xfs_da_btree.h
index 9fc699d..3a9b9e8 100644
--- a/fs/xfs/xfs_da_btree.h
+++ b/fs/xfs/xfs_da_btree.h
@@ -296,8 +296,6 @@
 /*
  * Utility routines.
  */
-int	xfs_da_blk_unlink(xfs_da_state_t *state, xfs_da_state_blk_t *drop_blk,
-					 xfs_da_state_blk_t *save_blk);
 int	xfs_da_blk_link(xfs_da_state_t *state, xfs_da_state_blk_t *old_blk,
 				       xfs_da_state_blk_t *new_blk);
 
@@ -320,7 +318,6 @@
 uint xfs_da_log2_roundup(uint i);
 xfs_da_state_t *xfs_da_state_alloc(void);
 void xfs_da_state_free(xfs_da_state_t *state);
-void xfs_da_state_kill_altpath(xfs_da_state_t *state);
 
 void xfs_da_buf_done(xfs_dabuf_t *dabuf);
 void xfs_da_log_buf(struct xfs_trans *tp, xfs_dabuf_t *dabuf, uint first,
diff --git a/fs/xfs/xfs_dfrag.c b/fs/xfs/xfs_dfrag.c
index 63abdc2..681be5c 100644
--- a/fs/xfs/xfs_dfrag.c
+++ b/fs/xfs/xfs_dfrag.c
@@ -180,9 +180,10 @@
 		goto error0;
 	}
 
-	if (VN_CACHED(tvp) != 0)
-		xfs_inval_cached_pages(XFS_ITOV(tip), &(tip->i_iocore),
-						(xfs_off_t)0, 0, 0);
+	if (VN_CACHED(tvp) != 0) {
+		xfs_inval_cached_trace(&tip->i_iocore, 0, -1, 0, -1);
+		VOP_FLUSHINVAL_PAGES(tvp, 0, -1, FI_REMAPF_LOCKED);
+	}
 
 	/* Verify O_DIRECT for ftmp */
 	if (VN_CACHED(tvp) != 0) {
diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c
index db9887a..a0aa0e4 100644
--- a/fs/xfs/xfs_dir2_data.c
+++ b/fs/xfs/xfs_dir2_data.c
@@ -304,7 +304,7 @@
 /*
  * Remove a bestfree entry from the table.
  */
-void
+STATIC void
 xfs_dir2_data_freeremove(
 	xfs_dir2_data_t		*d,		/* data block pointer */
 	xfs_dir2_data_free_t	*dfp,		/* bestfree entry pointer */
diff --git a/fs/xfs/xfs_dir2_data.h b/fs/xfs/xfs_dir2_data.h
index 3f02294..476cac9 100644
--- a/fs/xfs/xfs_dir2_data.h
+++ b/fs/xfs/xfs_dir2_data.h
@@ -193,10 +193,6 @@
 				 xfs_dir2_data_unused_t *dup, int *loghead);
 
 extern void
-	xfs_dir2_data_freeremove(xfs_dir2_data_t *d,
-				 xfs_dir2_data_free_t *dfp, int *loghead);
-
-extern void
 	xfs_dir2_data_freescan(struct xfs_mount *mp, xfs_dir2_data_t *d,
 			       int *loghead, char *aendp);
 
diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c
index 262d1e8..056f528 100644
--- a/fs/xfs/xfs_dir2_leaf.c
+++ b/fs/xfs/xfs_dir2_leaf.c
@@ -77,6 +77,10 @@
 #endif
 static int xfs_dir2_leaf_lookup_int(xfs_da_args_t *args, xfs_dabuf_t **lbpp,
 				    int *indexp, xfs_dabuf_t **dbpp);
+static void xfs_dir2_leaf_log_bests(struct xfs_trans *tp, struct xfs_dabuf *bp,
+				    int first, int last);
+static void xfs_dir2_leaf_log_tail(struct xfs_trans *tp, struct xfs_dabuf *bp);
+
 
 /*
  * Convert a block form directory to a leaf form directory.
@@ -1214,7 +1218,7 @@
 /*
  * Log the bests entries indicated from a leaf1 block.
  */
-void
+static void
 xfs_dir2_leaf_log_bests(
 	xfs_trans_t		*tp,		/* transaction pointer */
 	xfs_dabuf_t		*bp,		/* leaf buffer */
@@ -1278,7 +1282,7 @@
 /*
  * Log the tail of the leaf1 block.
  */
-void
+STATIC void
 xfs_dir2_leaf_log_tail(
 	xfs_trans_t		*tp,		/* transaction pointer */
 	xfs_dabuf_t		*bp)		/* leaf buffer */
diff --git a/fs/xfs/xfs_dir2_leaf.h b/fs/xfs/xfs_dir2_leaf.h
index 7f20eee..3303cd6 100644
--- a/fs/xfs/xfs_dir2_leaf.h
+++ b/fs/xfs/xfs_dir2_leaf.h
@@ -330,15 +330,8 @@
 			       int first, int last);
 
 extern void
-	xfs_dir2_leaf_log_bests(struct xfs_trans *tp, struct xfs_dabuf *bp,
-				int first, int last);
-
-extern void
 	xfs_dir2_leaf_log_header(struct xfs_trans *tp, struct xfs_dabuf *bp);
 
-extern void
-	xfs_dir2_leaf_log_tail(struct xfs_trans *tp, struct xfs_dabuf *bp);
-
 extern int
 	xfs_dir2_leaf_lookup(struct xfs_da_args *args);
 
diff --git a/fs/xfs/xfs_dir_leaf.c b/fs/xfs/xfs_dir_leaf.c
index 617018d..c2ea617 100644
--- a/fs/xfs/xfs_dir_leaf.c
+++ b/fs/xfs/xfs_dir_leaf.c
@@ -91,6 +91,10 @@
 					  int *number_entries_in_blk1,
 					  int *number_namebytes_in_blk1);
 
+STATIC int xfs_dir_leaf_create(struct xfs_da_args *args,
+				xfs_dablk_t which_block,
+				struct xfs_dabuf **bpp);
+
 /*
  * Utility routines.
  */
@@ -781,7 +785,7 @@
  * Create the initial contents of a leaf directory
  * or a leaf in a node directory.
  */
-int
+STATIC int
 xfs_dir_leaf_create(xfs_da_args_t *args, xfs_dablk_t blkno, xfs_dabuf_t **bpp)
 {
 	xfs_dir_leafblock_t *leaf;
diff --git a/fs/xfs/xfs_dir_leaf.h b/fs/xfs/xfs_dir_leaf.h
index 00d68d3..dd423ce 100644
--- a/fs/xfs/xfs_dir_leaf.h
+++ b/fs/xfs/xfs_dir_leaf.h
@@ -202,8 +202,6 @@
 /*
  * Routines used for growing the Btree.
  */
-int	xfs_dir_leaf_create(struct xfs_da_args *args, xfs_dablk_t which_block,
-				   struct xfs_dabuf **bpp);
 int	xfs_dir_leaf_split(struct xfs_da_state *state,
 				  struct xfs_da_state_blk *oldblk,
 				  struct xfs_da_state_blk *newblk);
diff --git a/fs/xfs/xfs_dmapi.h b/fs/xfs/xfs_dmapi.h
index 55ae3e6..55c17ad 100644
--- a/fs/xfs/xfs_dmapi.h
+++ b/fs/xfs/xfs_dmapi.h
@@ -166,27 +166,32 @@
 #define DM_FLAGS_NDELAY		0x001	/* return EAGAIN after dm_pending() */
 #define DM_FLAGS_UNWANTED	0x002	/* event not in fsys dm_eventset_t */
 #define DM_FLAGS_ISEM		0x004	/* thread holds i_sem */
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0)
-#if LINUX_VERSION_CODE > KERNEL_VERSION(2,4,21)
-/* i_alloc_sem was added in 2.4.22-pre1 */
 #define DM_FLAGS_IALLOCSEM_RD	0x010	/* thread holds i_alloc_sem rd */
 #define DM_FLAGS_IALLOCSEM_WR	0x020	/* thread holds i_alloc_sem wr */
-#endif
-#endif
 
 /*
  *	Based on IO_ISDIRECT, decide which i_ flag is set.
  */
-#ifdef DM_FLAGS_IALLOCSEM_RD
+#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0)
+#define DM_SEM_FLAG_RD(ioflags) (((ioflags) & IO_ISDIRECT) ? \
+			      DM_FLAGS_ISEM : 0)
+#define DM_SEM_FLAG_WR	(DM_FLAGS_IALLOCSEM_WR | DM_FLAGS_ISEM)
+#endif
+
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0)) && \
+    (LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22))
 #define DM_SEM_FLAG_RD(ioflags) (((ioflags) & IO_ISDIRECT) ? \
 			      DM_FLAGS_IALLOCSEM_RD : DM_FLAGS_ISEM)
 #define DM_SEM_FLAG_WR	(DM_FLAGS_IALLOCSEM_WR | DM_FLAGS_ISEM)
-#else
+#endif
+
+#if LINUX_VERSION_CODE <= KERNEL_VERSION(2,4,21)
 #define DM_SEM_FLAG_RD(ioflags) (((ioflags) & IO_ISDIRECT) ? \
 			      0 : DM_FLAGS_ISEM)
 #define DM_SEM_FLAG_WR	(DM_FLAGS_ISEM)
 #endif
 
+
 /*
  *	Macros to turn caller specified delay/block flags into
  *	dm_send_xxxx_event flag DM_FLAGS_NDELAY.
diff --git a/fs/xfs/xfs_error.c b/fs/xfs/xfs_error.c
index bbe1dea..dcd3fdd 100644
--- a/fs/xfs/xfs_error.c
+++ b/fs/xfs/xfs_error.c
@@ -280,7 +280,7 @@
 	}
 }
 
-void
+STATIC void
 xfs_hex_dump(void *p, int length)
 {
 	__uint8_t *uip = (__uint8_t*)p;
diff --git a/fs/xfs/xfs_error.h b/fs/xfs/xfs_error.h
index 6bc0535..52ee2b9 100644
--- a/fs/xfs/xfs_error.h
+++ b/fs/xfs/xfs_error.h
@@ -73,9 +73,6 @@
 	int		linenum,
 	inst_t		*ra);
 
-extern void
-xfs_hex_dump(void *p, int length);
-
 #define	XFS_ERROR_REPORT(e, lvl, mp)	\
 	xfs_error_report(e, lvl, mp, __FILE__, __LINE__, __return_address)
 #define	XFS_CORRUPTION_ERROR(e, lvl, mp, mem)	\
diff --git a/fs/xfs/xfs_extfree_item.c b/fs/xfs/xfs_extfree_item.c
index 5eafd5b..db7cbd1 100644
--- a/fs/xfs/xfs_extfree_item.c
+++ b/fs/xfs/xfs_extfree_item.c
@@ -59,6 +59,18 @@
 STATIC void	xfs_efd_item_abort(xfs_efd_log_item_t *);
 
 
+void
+xfs_efi_item_free(xfs_efi_log_item_t *efip)
+{
+	int nexts = efip->efi_format.efi_nextents;
+
+	if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
+		kmem_free(efip, sizeof(xfs_efi_log_item_t) +
+				(nexts - 1) * sizeof(xfs_extent_t));
+	} else {
+		kmem_zone_free(xfs_efi_zone, efip);
+	}
+}
 
 /*
  * This returns the number of iovecs needed to log the given efi item.
@@ -120,8 +132,6 @@
 STATIC void
 xfs_efi_item_unpin(xfs_efi_log_item_t *efip, int stale)
 {
-	int		nexts;
-	int		size;
 	xfs_mount_t	*mp;
 	SPLDECL(s);
 
@@ -132,21 +142,11 @@
 		 * xfs_trans_delete_ail() drops the AIL lock.
 		 */
 		xfs_trans_delete_ail(mp, (xfs_log_item_t *)efip, s);
-
-		nexts = efip->efi_format.efi_nextents;
-		if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
-			size = sizeof(xfs_efi_log_item_t);
-			size += (nexts - 1) * sizeof(xfs_extent_t);
-			kmem_free(efip, size);
-		} else {
-			kmem_zone_free(xfs_efi_zone, efip);
-		}
+		xfs_efi_item_free(efip);
 	} else {
 		efip->efi_flags |= XFS_EFI_COMMITTED;
 		AIL_UNLOCK(mp, s);
 	}
-
-	return;
 }
 
 /*
@@ -159,8 +159,6 @@
 STATIC void
 xfs_efi_item_unpin_remove(xfs_efi_log_item_t *efip, xfs_trans_t *tp)
 {
-	int		nexts;
-	int		size;
 	xfs_mount_t	*mp;
 	xfs_log_item_desc_t	*lidp;
 	SPLDECL(s);
@@ -178,23 +176,11 @@
 		 * xfs_trans_delete_ail() drops the AIL lock.
 		 */
 		xfs_trans_delete_ail(mp, (xfs_log_item_t *)efip, s);
-		/*
-		 * now free the item itself
-		 */
-		nexts = efip->efi_format.efi_nextents;
-		if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
-			size = sizeof(xfs_efi_log_item_t);
-			size += (nexts - 1) * sizeof(xfs_extent_t);
-			kmem_free(efip, size);
-		} else {
-			kmem_zone_free(xfs_efi_zone, efip);
-		}
+		xfs_efi_item_free(efip);
 	} else {
 		efip->efi_flags |= XFS_EFI_COMMITTED;
 		AIL_UNLOCK(mp, s);
 	}
-
-	return;
 }
 
 /*
@@ -245,18 +231,7 @@
 STATIC void
 xfs_efi_item_abort(xfs_efi_log_item_t *efip)
 {
-	int	nexts;
-	int	size;
-
-	nexts = efip->efi_format.efi_nextents;
-	if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
-		size = sizeof(xfs_efi_log_item_t);
-		size += (nexts - 1) * sizeof(xfs_extent_t);
-		kmem_free(efip, size);
-	} else {
-		kmem_zone_free(xfs_efi_zone, efip);
-	}
-	return;
+	xfs_efi_item_free(efip);
 }
 
 /*
@@ -288,7 +263,7 @@
 /*
  * This is the ops vector shared by all efi log items.
  */
-struct xfs_item_ops xfs_efi_item_ops = {
+STATIC struct xfs_item_ops xfs_efi_item_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_efi_item_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_efi_item_format,
@@ -355,8 +330,6 @@
 {
 	xfs_mount_t	*mp;
 	int		extents_left;
-	uint		size;
-	int		nexts;
 	SPLDECL(s);
 
 	mp = efip->efi_item.li_mountp;
@@ -372,20 +345,10 @@
 		 * xfs_trans_delete_ail() drops the AIL lock.
 		 */
 		xfs_trans_delete_ail(mp, (xfs_log_item_t *)efip, s);
+		xfs_efi_item_free(efip);
 	} else {
 		AIL_UNLOCK(mp, s);
 	}
-
-	if (extents_left == 0) {
-		nexts = efip->efi_format.efi_nextents;
-		if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
-			size = sizeof(xfs_efi_log_item_t);
-			size += (nexts - 1) * sizeof(xfs_extent_t);
-			kmem_free(efip, size);
-		} else {
-			kmem_zone_free(xfs_efi_zone, efip);
-		}
-	}
 }
 
 /*
@@ -398,8 +361,6 @@
 xfs_efi_cancel(
 	xfs_efi_log_item_t	*efip)
 {
-	int		nexts;
-	int		size;
 	xfs_mount_t	*mp;
 	SPLDECL(s);
 
@@ -410,26 +371,25 @@
 		 * xfs_trans_delete_ail() drops the AIL lock.
 		 */
 		xfs_trans_delete_ail(mp, (xfs_log_item_t *)efip, s);
-
-		nexts = efip->efi_format.efi_nextents;
-		if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
-			size = sizeof(xfs_efi_log_item_t);
-			size += (nexts - 1) * sizeof(xfs_extent_t);
-			kmem_free(efip, size);
-		} else {
-			kmem_zone_free(xfs_efi_zone, efip);
-		}
+		xfs_efi_item_free(efip);
 	} else {
 		efip->efi_flags |= XFS_EFI_CANCELED;
 		AIL_UNLOCK(mp, s);
 	}
-
-	return;
 }
 
+STATIC void
+xfs_efd_item_free(xfs_efd_log_item_t *efdp)
+{
+	int nexts = efdp->efd_format.efd_nextents;
 
-
-
+	if (nexts > XFS_EFD_MAX_FAST_EXTENTS) {
+		kmem_free(efdp, sizeof(xfs_efd_log_item_t) +
+				(nexts - 1) * sizeof(xfs_extent_t));
+	} else {
+		kmem_zone_free(xfs_efd_zone, efdp);
+	}
+}
 
 /*
  * This returns the number of iovecs needed to log the given efd item.
@@ -533,9 +493,6 @@
 STATIC xfs_lsn_t
 xfs_efd_item_committed(xfs_efd_log_item_t *efdp, xfs_lsn_t lsn)
 {
-	uint	size;
-	int	nexts;
-
 	/*
 	 * If we got a log I/O error, it's always the case that the LR with the
 	 * EFI got unpinned and freed before the EFD got aborted.
@@ -543,15 +500,7 @@
 	if ((efdp->efd_item.li_flags & XFS_LI_ABORTED) == 0)
 		xfs_efi_release(efdp->efd_efip, efdp->efd_format.efd_nextents);
 
-	nexts = efdp->efd_format.efd_nextents;
-	if (nexts > XFS_EFD_MAX_FAST_EXTENTS) {
-		size = sizeof(xfs_efd_log_item_t);
-		size += (nexts - 1) * sizeof(xfs_extent_t);
-		kmem_free(efdp, size);
-	} else {
-		kmem_zone_free(xfs_efd_zone, efdp);
-	}
-
+	xfs_efd_item_free(efdp);
 	return (xfs_lsn_t)-1;
 }
 
@@ -565,9 +514,6 @@
 STATIC void
 xfs_efd_item_abort(xfs_efd_log_item_t *efdp)
 {
-	int	nexts;
-	int	size;
-
 	/*
 	 * If we got a log I/O error, it's always the case that the LR with the
 	 * EFI got unpinned and freed before the EFD got aborted. So don't
@@ -576,15 +522,7 @@
 	if ((efdp->efd_item.li_flags & XFS_LI_ABORTED) == 0)
 		xfs_efi_cancel(efdp->efd_efip);
 
-	nexts = efdp->efd_format.efd_nextents;
-	if (nexts > XFS_EFD_MAX_FAST_EXTENTS) {
-		size = sizeof(xfs_efd_log_item_t);
-		size += (nexts - 1) * sizeof(xfs_extent_t);
-		kmem_free(efdp, size);
-	} else {
-		kmem_zone_free(xfs_efd_zone, efdp);
-	}
-	return;
+	xfs_efd_item_free(efdp);
 }
 
 /*
@@ -615,7 +553,7 @@
 /*
  * This is the ops vector shared by all efd log items.
  */
-struct xfs_item_ops xfs_efd_item_ops = {
+STATIC struct xfs_item_ops xfs_efd_item_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_efd_item_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_efd_item_format,
diff --git a/fs/xfs/xfs_extfree_item.h b/fs/xfs/xfs_extfree_item.h
index 7122d61..d433bac 100644
--- a/fs/xfs/xfs_extfree_item.h
+++ b/fs/xfs/xfs_extfree_item.h
@@ -118,6 +118,8 @@
 xfs_efd_log_item_t	*xfs_efd_init(struct xfs_mount *, xfs_efi_log_item_t *,
 				      uint);
 
+void			xfs_efi_item_free(xfs_efi_log_item_t *);
+
 #endif	/* __KERNEL__ */
 
 #endif	/* __XFS_EXTFREE_ITEM_H__ */
diff --git a/fs/xfs/xfs_fs.h b/fs/xfs/xfs_fs.h
index 6ee8443..095af0a 100644
--- a/fs/xfs/xfs_fs.h
+++ b/fs/xfs/xfs_fs.h
@@ -60,7 +60,8 @@
 	__u32		fsx_xflags;	/* xflags field value (get/set) */
 	__u32		fsx_extsize;	/* extsize field value (get/set)*/
 	__u32		fsx_nextents;	/* nextents field value (get)	*/
-	unsigned char	fsx_pad[16];
+	__u32		fsx_projid;	/* project identifier (get/set) */
+	unsigned char	fsx_pad[12];
 };
 #endif
 
diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c
index 2121305..ca535d6 100644
--- a/fs/xfs/xfs_fsops.c
+++ b/fs/xfs/xfs_fsops.c
@@ -559,32 +559,6 @@
 	return(0);
 }
 
-void
-xfs_fs_log_dummy(xfs_mount_t *mp)
-{
-	xfs_trans_t *tp;
-	xfs_inode_t *ip;
-
-
-	tp = _xfs_trans_alloc(mp, XFS_TRANS_DUMMY1);
-	atomic_inc(&mp->m_active_trans);
-	if (xfs_trans_reserve(tp, 0, XFS_ICHANGE_LOG_RES(mp), 0, 0, 0)) {
-		xfs_trans_cancel(tp, 0);
-		return;
-	}
-
-	ip = mp->m_rootip;
-	xfs_ilock(ip, XFS_ILOCK_EXCL);
-
-	xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL);
-	xfs_trans_ihold(tp, ip);
-	xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
-	xfs_trans_set_sync(tp);
-	xfs_trans_commit(tp, 0, NULL);
-
-	xfs_iunlock(ip, XFS_ILOCK_EXCL);
-}
-
 int
 xfs_fs_goingdown(
 	xfs_mount_t	*mp,
diff --git a/fs/xfs/xfs_ialloc_btree.h b/fs/xfs/xfs_ialloc_btree.h
index 803c4d1..44be188 100644
--- a/fs/xfs/xfs_ialloc_btree.h
+++ b/fs/xfs/xfs_ialloc_btree.h
@@ -100,9 +100,13 @@
 #endif
 #if XFS_WANT_FUNCS || (XFS_WANT_SPACE && XFSSO_XFS_INOBT_IS_FREE)
 int xfs_inobt_is_free(xfs_inobt_rec_t *rp, int i);
-#define	XFS_INOBT_IS_FREE(rp,i)	xfs_inobt_is_free(rp,i)
+#define	XFS_INOBT_IS_FREE(rp,i)		xfs_inobt_is_free(rp,i)
+#define	XFS_INOBT_IS_FREE_DISK(rp,i)	xfs_inobt_is_free_disk(rp,i)
 #else
-#define	XFS_INOBT_IS_FREE(rp,i)	(((rp)->ir_free & XFS_INOBT_MASK(i)) != 0)
+#define	XFS_INOBT_IS_FREE(rp,i)	\
+	(((rp)->ir_free & XFS_INOBT_MASK(i)) != 0)
+#define XFS_INOBT_IS_FREE_DISK(rp,i) \
+	((INT_GET((rp)->ir_free, ARCH_CONVERT) & XFS_INOBT_MASK(i)) != 0)
 #endif
 #if XFS_WANT_FUNCS || (XFS_WANT_SPACE && XFSSO_XFS_INOBT_SET_FREE)
 void xfs_inobt_set_free(xfs_inobt_rec_t *rp, int i);
diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c
index bc8c8c7..34bdf59 100644
--- a/fs/xfs/xfs_inode.c
+++ b/fs/xfs/xfs_inode.c
@@ -146,51 +146,6 @@
 #endif
 
 /*
- * called from bwrite on xfs inode buffers
- */
-void
-xfs_inobp_bwcheck(xfs_buf_t *bp)
-{
-	xfs_mount_t	*mp;
-	int		i;
-	int		j;
-	xfs_dinode_t	*dip;
-
-	ASSERT(XFS_BUF_FSPRIVATE3(bp, void *) != NULL);
-
-	mp = XFS_BUF_FSPRIVATE3(bp, xfs_mount_t *);
-
-
-	j = mp->m_inode_cluster_size >> mp->m_sb.sb_inodelog;
-
-	for (i = 0; i < j; i++)  {
-		dip = (xfs_dinode_t *) xfs_buf_offset(bp,
-						i * mp->m_sb.sb_inodesize);
-		if (INT_GET(dip->di_core.di_magic, ARCH_CONVERT) != XFS_DINODE_MAGIC) {
-			cmn_err(CE_WARN,
-"Bad magic # 0x%x in XFS inode buffer 0x%Lx, starting blockno %Ld, offset 0x%x",
-				INT_GET(dip->di_core.di_magic, ARCH_CONVERT),
-				(__uint64_t)(__psunsigned_t) bp,
-				(__int64_t) XFS_BUF_ADDR(bp),
-				xfs_buf_offset(bp, i * mp->m_sb.sb_inodesize));
-			xfs_fs_cmn_err(CE_WARN, mp,
-				"corrupt, unmount and run xfs_repair");
-		}
-		if (!dip->di_next_unlinked)  {
-			cmn_err(CE_WARN,
-"Bad next_unlinked field (0) in XFS inode buffer 0x%p, starting blockno %Ld, offset 0x%x",
-				(__uint64_t)(__psunsigned_t) bp,
-				(__int64_t) XFS_BUF_ADDR(bp),
-				xfs_buf_offset(bp, i * mp->m_sb.sb_inodesize));
-			xfs_fs_cmn_err(CE_WARN, mp,
-				"corrupt, unmount and run xfs_repair");
-		}
-	}
-
-	return;
-}
-
-/*
  * This routine is called to map an inode number within a file
  * system to the buffer containing the on-disk version of the
  * inode.  It returns a pointer to the buffer containing the
@@ -203,7 +158,7 @@
  * Use xfs_imap() to determine the size and location of the
  * buffer to read from disk.
  */
-int
+STATIC int
 xfs_inotobp(
 	xfs_mount_t	*mp,
 	xfs_trans_t	*tp,
@@ -1247,26 +1202,32 @@
 	case S_IFREG:
 	case S_IFDIR:
 		if (unlikely(pip->i_d.di_flags & XFS_DIFLAG_ANY)) {
-			if (pip->i_d.di_flags & XFS_DIFLAG_RTINHERIT) {
-				if ((mode & S_IFMT) == S_IFDIR) {
-					ip->i_d.di_flags |= XFS_DIFLAG_RTINHERIT;
-				} else {
-					ip->i_d.di_flags |= XFS_DIFLAG_REALTIME;
+			uint	di_flags = 0;
+
+			if ((mode & S_IFMT) == S_IFDIR) {
+				if (pip->i_d.di_flags & XFS_DIFLAG_RTINHERIT)
+					di_flags |= XFS_DIFLAG_RTINHERIT;
+			} else {
+				if (pip->i_d.di_flags & XFS_DIFLAG_RTINHERIT) {
+					di_flags |= XFS_DIFLAG_REALTIME;
 					ip->i_iocore.io_flags |= XFS_IOCORE_RT;
 				}
 			}
 			if ((pip->i_d.di_flags & XFS_DIFLAG_NOATIME) &&
 			    xfs_inherit_noatime)
-				ip->i_d.di_flags |= XFS_DIFLAG_NOATIME;
+				di_flags |= XFS_DIFLAG_NOATIME;
 			if ((pip->i_d.di_flags & XFS_DIFLAG_NODUMP) &&
 			    xfs_inherit_nodump)
-				ip->i_d.di_flags |= XFS_DIFLAG_NODUMP;
+				di_flags |= XFS_DIFLAG_NODUMP;
 			if ((pip->i_d.di_flags & XFS_DIFLAG_SYNC) &&
 			    xfs_inherit_sync)
-				ip->i_d.di_flags |= XFS_DIFLAG_SYNC;
+				di_flags |= XFS_DIFLAG_SYNC;
 			if ((pip->i_d.di_flags & XFS_DIFLAG_NOSYMLINKS) &&
 			    xfs_inherit_nosymlinks)
-				ip->i_d.di_flags |= XFS_DIFLAG_NOSYMLINKS;
+				di_flags |= XFS_DIFLAG_NOSYMLINKS;
+			if (pip->i_d.di_flags & XFS_DIFLAG_PROJINHERIT)
+				di_flags |= XFS_DIFLAG_PROJINHERIT;
+			ip->i_d.di_flags |= di_flags;
 		}
 		/* FALLTHROUGH */
 	case S_IFLNK:
@@ -2156,7 +2117,7 @@
 		(ip->i_update_core == 0));
 }
 
-void
+STATIC void
 xfs_ifree_cluster(
 	xfs_inode_t	*free_ip,
 	xfs_trans_t	*tp,
@@ -2875,7 +2836,7 @@
  * be subsequently pinned once someone is waiting for it to be
  * unpinned.
  */
-void
+STATIC void
 xfs_iunpin_wait(
 	xfs_inode_t	*ip)
 {
@@ -3601,106 +3562,42 @@
 
 
 /*
- * Flush all inactive inodes in mp.  Return true if no user references
- * were found, false otherwise.
+ * Flush all inactive inodes in mp.
  */
-int
+void
 xfs_iflush_all(
-	xfs_mount_t	*mp,
-	int		flag)
+	xfs_mount_t	*mp)
 {
-	int		busy;
-	int		done;
-	int		purged;
 	xfs_inode_t	*ip;
-	vmap_t		vmap;
 	vnode_t		*vp;
 
-	busy = done = 0;
-	while (!done) {
-		purged = 0;
-		XFS_MOUNT_ILOCK(mp);
-		ip = mp->m_inodes;
-		if (ip == NULL) {
-			break;
+ again:
+	XFS_MOUNT_ILOCK(mp);
+	ip = mp->m_inodes;
+	if (ip == NULL)
+		goto out;
+
+	do {
+		/* Make sure we skip markers inserted by sync */
+		if (ip->i_mount == NULL) {
+			ip = ip->i_mnext;
+			continue;
 		}
-		do {
-			/* Make sure we skip markers inserted by sync */
-			if (ip->i_mount == NULL) {
-				ip = ip->i_mnext;
-				continue;
-			}
 
-			/*
-			 * It's up to our caller to purge the root
-			 * and quota vnodes later.
-			 */
-			vp = XFS_ITOV_NULL(ip);
-
-			if (!vp) {
-				XFS_MOUNT_IUNLOCK(mp);
-				xfs_finish_reclaim(ip, 0, XFS_IFLUSH_ASYNC);
-				purged = 1;
-				break;
-			}
-
-			if (vn_count(vp) != 0) {
-				if (vn_count(vp) == 1 &&
-				    (ip == mp->m_rootip ||
-				     (mp->m_quotainfo &&
-				      (ip->i_ino == mp->m_sb.sb_uquotino ||
-				       ip->i_ino == mp->m_sb.sb_gquotino)))) {
-
-					ip = ip->i_mnext;
-					continue;
-				}
-				if (!(flag & XFS_FLUSH_ALL)) {
-					busy = 1;
-					done = 1;
-					break;
-				}
-				/*
-				 * Ignore busy inodes but continue flushing
-				 * others.
-				 */
-				ip = ip->i_mnext;
-				continue;
-			}
-			/*
-			 * Sample vp mapping while holding mp locked on MP
-			 * systems, so we don't purge a reclaimed or
-			 * nonexistent vnode.  We break from the loop
-			 * since we know that we modify
-			 * it by pulling ourselves from it in xfs_reclaim()
-			 * called via vn_purge() below.  Set ip to the next
-			 * entry in the list anyway so we'll know below
-			 * whether we reached the end or not.
-			 */
-			VMAP(vp, vmap);
+		vp = XFS_ITOV_NULL(ip);
+		if (!vp) {
 			XFS_MOUNT_IUNLOCK(mp);
-
-			vn_purge(vp, &vmap);
-
-			purged = 1;
-			break;
-		} while (ip != mp->m_inodes);
-		/*
-		 * We need to distinguish between when we exit the loop
-		 * after a purge and when we simply hit the end of the
-		 * list.  We can't use the (ip == mp->m_inodes) test,
-		 * because when we purge an inode at the start of the list
-		 * the next inode on the list becomes mp->m_inodes.  That
-		 * would cause such a test to bail out early.  The purged
-		 * variable tells us how we got out of the loop.
-		 */
-		if (!purged) {
-			done = 1;
+			xfs_finish_reclaim(ip, 0, XFS_IFLUSH_ASYNC);
+			goto again;
 		}
-	}
-	XFS_MOUNT_IUNLOCK(mp);
-	return !busy;
-}
 
+		ASSERT(vn_count(vp) == 0);
+
+		ip = ip->i_mnext;
+	} while (ip != mp->m_inodes);
+ out:
+	XFS_MOUNT_IUNLOCK(mp);
+}
 
 /*
  * xfs_iaccess: check accessibility of inode for mode.
diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h
index 37e1c31..54d9e54 100644
--- a/fs/xfs/xfs_inode.h
+++ b/fs/xfs/xfs_inode.h
@@ -412,11 +412,6 @@
 #define	XFS_IFLUSH_DELWRI		5
 
 /*
- * Flags for xfs_iflush_all.
- */
-#define	XFS_FLUSH_ALL		0x1
-
-/*
  * Flags for xfs_itruncate_start().
  */
 #define	XFS_ITRUNC_DEFINITE	0x1
@@ -487,8 +482,6 @@
 /*
  * xfs_inode.c prototypes.
  */
-int		xfs_inotobp(struct xfs_mount *, struct xfs_trans *, xfs_ino_t,
-			    xfs_dinode_t **, struct xfs_buf **, int *);
 int		xfs_itobp(struct xfs_mount *, struct xfs_trans *,
 			  xfs_inode_t *, xfs_dinode_t **, struct xfs_buf **,
 			  xfs_daddr_t);
@@ -522,7 +515,7 @@
 void		xfs_iunpin(xfs_inode_t *);
 int		xfs_iextents_copy(xfs_inode_t *, xfs_bmbt_rec_t *, int);
 int		xfs_iflush(xfs_inode_t *, uint);
-int		xfs_iflush_all(struct xfs_mount *, int);
+void		xfs_iflush_all(struct xfs_mount *);
 int		xfs_iaccess(xfs_inode_t *, mode_t, cred_t *);
 uint		xfs_iroundup(uint);
 void		xfs_ichgtime(xfs_inode_t *, int);
diff --git a/fs/xfs/xfs_inode_item.c b/fs/xfs/xfs_inode_item.c
index 768cb18..0eed30f 100644
--- a/fs/xfs/xfs_inode_item.c
+++ b/fs/xfs/xfs_inode_item.c
@@ -910,7 +910,7 @@
 /*
  * This is the ops vector shared by all buf log items.
  */
-struct xfs_item_ops xfs_inode_item_ops = {
+STATIC struct xfs_item_ops xfs_inode_item_ops = {
 	.iop_size	= (uint(*)(xfs_log_item_t*))xfs_inode_item_size,
 	.iop_format	= (void(*)(xfs_log_item_t*, xfs_log_iovec_t*))
 					xfs_inode_item_format,
diff --git a/fs/xfs/xfs_iomap.c b/fs/xfs/xfs_iomap.c
index 469e1a7..2edd676 100644
--- a/fs/xfs/xfs_iomap.c
+++ b/fs/xfs/xfs_iomap.c
@@ -385,15 +385,15 @@
 	int		nimaps, maps;
 	int		error;
 	int		bmapi_flag;
+	int		quota_flag;
 	int		rt;
 	xfs_trans_t	*tp;
 	xfs_bmbt_irec_t imap[XFS_WRITE_IMAPS], *imapp;
 	xfs_bmap_free_t free_list;
 	int		aeof;
-	xfs_filblks_t	datablocks;
+	xfs_filblks_t	datablocks, qblocks, resblks;
 	int		committed;
 	int		numrtextents;
-	uint		resblks;
 
 	/*
 	 * Make sure that the dquots are there. This doesn't hold
@@ -419,7 +419,6 @@
 		xfs_fileoff_t	map_last_fsb;
 
 		map_last_fsb = ret_imap->br_blockcount + ret_imap->br_startoff;
-
 		if (map_last_fsb < last_fsb) {
 			last_fsb = map_last_fsb;
 			count_fsb = last_fsb - offset_fsb;
@@ -428,56 +427,47 @@
 	}
 
 	/*
-	 * determine if reserving space on
-	 * the data or realtime partition.
+	 * Determine if reserving space on the data or realtime partition.
 	 */
 	if ((rt = XFS_IS_REALTIME_INODE(ip))) {
-		int	sbrtextsize, iprtextsize;
+		xfs_extlen_t	extsz;
 
-		sbrtextsize = mp->m_sb.sb_rextsize;
-		iprtextsize =
-			ip->i_d.di_extsize ? ip->i_d.di_extsize : sbrtextsize;
-		numrtextents = (count_fsb + iprtextsize - 1);
-		do_div(numrtextents, sbrtextsize);
+		if (!(extsz = ip->i_d.di_extsize))
+			extsz = mp->m_sb.sb_rextsize;
+		numrtextents = qblocks = (count_fsb + extsz - 1);
+		do_div(numrtextents, mp->m_sb.sb_rextsize);
+		quota_flag = XFS_QMOPT_RES_RTBLKS;
 		datablocks = 0;
 	} else {
-		datablocks = count_fsb;
+		datablocks = qblocks = count_fsb;
+		quota_flag = XFS_QMOPT_RES_REGBLKS;
 		numrtextents = 0;
 	}
 
 	/*
-	 * allocate and setup the transaction
+	 * Allocate and setup the transaction
 	 */
 	xfs_iunlock(ip, XFS_ILOCK_EXCL);
 	tp = xfs_trans_alloc(mp, XFS_TRANS_DIOSTRAT);
-
 	resblks = XFS_DIOSTRAT_SPACE_RES(mp, datablocks);
-
 	error = xfs_trans_reserve(tp, resblks,
 			XFS_WRITE_LOG_RES(mp), numrtextents,
 			XFS_TRANS_PERM_LOG_RES,
 			XFS_WRITE_LOG_COUNT);
 
 	/*
-	 * check for running out of space
+	 * Check for running out of space, note: need lock to return
 	 */
 	if (error)
-		/*
-		 * Free the transaction structure.
-		 */
 		xfs_trans_cancel(tp, 0);
-
 	xfs_ilock(ip, XFS_ILOCK_EXCL);
-
 	if (error)
-		goto error_out; /* Don't return in above if .. trans ..,
-					need lock to return */
+		goto error_out;
 
-	if (XFS_TRANS_RESERVE_BLKQUOTA(mp, tp, ip, resblks)) {
+	if (XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, tp, ip, qblocks, 0, quota_flag)) {
 		error = (EDQUOT);
 		goto error1;
 	}
-	nimaps = 1;
 
 	bmapi_flag = XFS_BMAPI_WRITE;
 	xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL);
@@ -487,31 +477,29 @@
 		bmapi_flag |= XFS_BMAPI_PREALLOC;
 
 	/*
-	 * issue the bmapi() call to allocate the blocks
+	 * Issue the bmapi() call to allocate the blocks
 	 */
 	XFS_BMAP_INIT(&free_list, &firstfsb);
+	nimaps = 1;
 	imapp = &imap[0];
 	error = xfs_bmapi(tp, ip, offset_fsb, count_fsb,
 		bmapi_flag, &firstfsb, 0, imapp, &nimaps, &free_list);
-	if (error) {
+	if (error)
 		goto error0;
-	}
 
 	/*
-	 * complete the transaction
+	 * Complete the transaction
 	 */
-
 	error = xfs_bmap_finish(&tp, &free_list, firstfsb, &committed);
-	if (error) {
+	if (error)
 		goto error0;
-	}
-
 	error = xfs_trans_commit(tp, XFS_TRANS_RELEASE_LOG_RES, NULL);
-	if (error) {
+	if (error)
 		goto error_out;
-	}
 
-	/* copy any maps to caller's array and return any error. */
+	/*
+	 * Copy any maps to caller's array and return any error.
+	 */
 	if (nimaps == 0) {
 		error = (ENOSPC);
 		goto error_out;
@@ -530,10 +518,11 @@
         }
 	return 0;
 
- error0:	/* Cancel bmap, unlock inode, and cancel trans */
+error0:	/* Cancel bmap, unlock inode, unreserve quota blocks, cancel trans */
 	xfs_bmap_cancel(&free_list);
+	XFS_TRANS_UNRESERVE_QUOTA_NBLKS(mp, tp, ip, qblocks, 0, quota_flag);
 
- error1:	/* Just cancel transaction */
+error1:	/* Just cancel transaction */
 	xfs_trans_cancel(tp, XFS_TRANS_RELEASE_LOG_RES | XFS_TRANS_ABORT);
 	*nmaps = 0;	/* nothing set-up here */
 
diff --git a/fs/xfs/xfs_log.c b/fs/xfs/xfs_log.c
index 092d5fb..1cd2ac1 100644
--- a/fs/xfs/xfs_log.c
+++ b/fs/xfs/xfs_log.c
@@ -134,7 +134,7 @@
 #define xlog_verify_tail_lsn(a,b,c)
 #endif
 
-int		xlog_iclogs_empty(xlog_t *log);
+STATIC int	xlog_iclogs_empty(xlog_t *log);
 
 #ifdef DEBUG
 int xlog_do_error = 0;
@@ -1857,7 +1857,7 @@
  *
  * State Change: DIRTY -> ACTIVE
  */
-void
+STATIC void
 xlog_state_clean_log(xlog_t *log)
 {
 	xlog_in_core_t	*iclog;
@@ -3542,7 +3542,7 @@
 	return (retval);
 }
 
-int
+STATIC int
 xlog_iclogs_empty(xlog_t *log)
 {
 	xlog_in_core_t	*iclog;
diff --git a/fs/xfs/xfs_log_priv.h b/fs/xfs/xfs_log_priv.h
index c31e3ce..1a1d452 100644
--- a/fs/xfs/xfs_log_priv.h
+++ b/fs/xfs/xfs_log_priv.h
@@ -535,7 +535,6 @@
 
 /* common routines */
 extern xfs_lsn_t xlog_assign_tail_lsn(struct xfs_mount *mp);
-extern int	 xlog_find_head(xlog_t *log, xfs_daddr_t *head_blk);
 extern int	 xlog_find_tail(xlog_t	*log,
 				xfs_daddr_t *head_blk,
 				xfs_daddr_t *tail_blk,
@@ -548,7 +547,6 @@
 extern struct xfs_buf *xlog_get_bp(xlog_t *, int);
 extern void	 xlog_put_bp(struct xfs_buf *);
 extern int	 xlog_bread(xlog_t *, xfs_daddr_t, int, struct xfs_buf *);
-extern xfs_caddr_t xlog_align(xlog_t *, xfs_daddr_t, int, struct xfs_buf *);
 
 /* iclog tracing */
 #define XLOG_TRACE_GRAB_FLUSH  1
diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c
index 9824b5b..0aac28d 100644
--- a/fs/xfs/xfs_log_recover.c
+++ b/fs/xfs/xfs_log_recover.c
@@ -148,7 +148,7 @@
  * The buffer is kept locked across the write and is returned locked.
  * This can only be used for synchronous log writes.
  */
-int
+STATIC int
 xlog_bwrite(
 	xlog_t		*log,
 	xfs_daddr_t	blk_no,
@@ -179,7 +179,7 @@
 	return error;
 }
 
-xfs_caddr_t
+STATIC xfs_caddr_t
 xlog_align(
 	xlog_t		*log,
 	xfs_daddr_t	blk_no,
@@ -528,7 +528,7 @@
  *
  * Return: zero if normal, non-zero if error.
  */
-int
+STATIC int
 xlog_find_head(
 	xlog_t 		*log,
 	xfs_daddr_t	*return_head_blk)
@@ -1964,7 +1964,8 @@
 		 * probably a good thing to do for other buf types also.
 		 */
 		error = 0;
-		if (buf_f->blf_flags & (XFS_BLI_UDQUOT_BUF|XFS_BLI_GDQUOT_BUF)) {
+		if (buf_f->blf_flags &
+		   (XFS_BLI_UDQUOT_BUF|XFS_BLI_PDQUOT_BUF|XFS_BLI_GDQUOT_BUF)) {
 			error = xfs_qm_dqcheck((xfs_disk_dquot_t *)
 					       item->ri_buf[i].i_addr,
 					       -1, 0, XFS_QMOPT_DOWARN,
@@ -2030,6 +2031,7 @@
 	}
 
 	if (INT_GET(ddq->d_flags, ARCH_CONVERT) != XFS_DQ_USER &&
+	    INT_GET(ddq->d_flags, ARCH_CONVERT) != XFS_DQ_PROJ &&
 	    INT_GET(ddq->d_flags, ARCH_CONVERT) != XFS_DQ_GROUP) {
 		if (flags & XFS_QMOPT_DOWARN)
 			cmn_err(CE_ALERT,
@@ -2135,6 +2137,8 @@
 	type = 0;
 	if (buf_f->blf_flags & XFS_BLI_UDQUOT_BUF)
 		type |= XFS_DQ_USER;
+	if (buf_f->blf_flags & XFS_BLI_PDQUOT_BUF)
+		type |= XFS_DQ_PROJ;
 	if (buf_f->blf_flags & XFS_BLI_GDQUOT_BUF)
 		type |= XFS_DQ_GROUP;
 	/*
@@ -2247,7 +2251,8 @@
 	error = 0;
 	if (flags & XFS_BLI_INODE_BUF) {
 		error = xlog_recover_do_inode_buffer(mp, item, bp, buf_f);
-	} else if (flags & (XFS_BLI_UDQUOT_BUF | XFS_BLI_GDQUOT_BUF)) {
+	} else if (flags &
+		  (XFS_BLI_UDQUOT_BUF|XFS_BLI_PDQUOT_BUF|XFS_BLI_GDQUOT_BUF)) {
 		xlog_recover_do_dquot_buffer(mp, log, item, bp, buf_f);
 	} else {
 		xlog_recover_do_reg_buffer(mp, item, bp, buf_f);
@@ -2619,7 +2624,7 @@
 	 * This type of quotas was turned off, so ignore this record.
 	 */
 	type = INT_GET(recddq->d_flags, ARCH_CONVERT) &
-			(XFS_DQ_USER | XFS_DQ_GROUP);
+			(XFS_DQ_USER | XFS_DQ_PROJ | XFS_DQ_GROUP);
 	ASSERT(type);
 	if (log->l_quotaoffs_flag & type)
 		return (0);
@@ -2742,7 +2747,6 @@
 	xfs_efi_log_item_t	*efip = NULL;
 	xfs_log_item_t		*lip;
 	int			gen;
-	int			nexts;
 	__uint64_t		efi_id;
 	SPLDECL(s);
 
@@ -2777,22 +2781,15 @@
 		}
 		lip = xfs_trans_next_ail(mp, lip, &gen, NULL);
 	}
-	if (lip == NULL) {
-		AIL_UNLOCK(mp, s);
-	}
 
 	/*
 	 * If we found it, then free it up.  If it wasn't there, it
 	 * must have been overwritten in the log.  Oh well.
 	 */
 	if (lip != NULL) {
-		nexts = efip->efi_format.efi_nextents;
-		if (nexts > XFS_EFI_MAX_FAST_EXTENTS) {
-			kmem_free(lip, sizeof(xfs_efi_log_item_t) +
-				  ((nexts - 1) * sizeof(xfs_extent_t)));
-		} else {
-			kmem_zone_free(xfs_efi_zone, efip);
-		}
+		xfs_efi_item_free(efip);
+	} else {
+		AIL_UNLOCK(mp, s);
 	}
 }
 
diff --git a/fs/xfs/xfs_macros.c b/fs/xfs/xfs_macros.c
index ce4f46c..698c2cd 100644
--- a/fs/xfs/xfs_macros.c
+++ b/fs/xfs/xfs_macros.c
@@ -1658,6 +1658,11 @@
 {
 	return XFS_INOBT_IS_FREE(rp, i);
 }
+int
+xfs_inobt_is_free_disk(xfs_inobt_rec_t *rp, int i)
+{
+	return XFS_INOBT_IS_FREE_DISK(rp, i);
+}
 #endif
 
 #if XFS_WANT_FUNCS_C || (XFS_WANT_SPACE_C && XFSSO_XFS_INOBT_IS_LAST_REC)
diff --git a/fs/xfs/xfs_mount.c b/fs/xfs/xfs_mount.c
index 2ec967d..82e1646 100644
--- a/fs/xfs/xfs_mount.c
+++ b/fs/xfs/xfs_mount.c
@@ -64,6 +64,7 @@
 STATIC void	xfs_mount_log_sbunit(xfs_mount_t *, __int64_t);
 STATIC int	xfs_uuid_mount(xfs_mount_t *);
 STATIC void	xfs_uuid_unmount(xfs_mount_t *mp);
+STATIC void	xfs_unmountfs_wait(xfs_mount_t *);
 
 static struct {
     short offset;
@@ -555,7 +556,7 @@
  * fields from the superblock associated with the given
  * mount structure
  */
-void
+STATIC void
 xfs_mount_common(xfs_mount_t *mp, xfs_sb_t *sbp)
 {
 	int	i;
@@ -1081,7 +1082,7 @@
 	int64_t		fsid;
 #endif
 
-	xfs_iflush_all(mp, XFS_FLUSH_ALL);
+	xfs_iflush_all(mp);
 
 	XFS_QM_DQPURGEALL(mp,
 		XFS_QMOPT_UQUOTA | XFS_QMOPT_GQUOTA | XFS_QMOPT_UMOUNTING);
@@ -1111,15 +1112,6 @@
 	 */
 	ASSERT(mp->m_inodes == NULL);
 
-	/*
-	 * We may have bufs that are in the process of getting written still.
-	 * We must wait for the I/O completion of those. The sync flag here
-	 * does a two pass iteration thru the bufcache.
-	 */
-	if (XFS_FORCED_SHUTDOWN(mp)) {
-		xfs_incore_relse(mp->m_ddev_targp, 0, 1); /* synchronous */
-	}
-
 	xfs_unmountfs_close(mp, cr);
 	if ((mp->m_flags & XFS_MOUNT_NOUUID) == 0)
 		xfs_uuid_unmount(mp);
@@ -1146,7 +1138,7 @@
 	xfs_free_buftarg(mp->m_ddev_targp, 0);
 }
 
-void
+STATIC void
 xfs_unmountfs_wait(xfs_mount_t *mp)
 {
 	if (mp->m_logdev_targp != mp->m_ddev_targp)
diff --git a/fs/xfs/xfs_mount.h b/fs/xfs/xfs_mount.h
index 30dd08f..5affba3 100644
--- a/fs/xfs/xfs_mount.h
+++ b/fs/xfs/xfs_mount.h
@@ -141,7 +141,7 @@
 typedef void	(*xfs_dqdetach_t)(struct xfs_inode *);
 typedef int	(*xfs_dqpurgeall_t)(struct xfs_mount *, uint);
 typedef int	(*xfs_dqvopalloc_t)(struct xfs_mount *,
-			struct xfs_inode *, uid_t, gid_t, uint,
+			struct xfs_inode *, uid_t, gid_t, prid_t, uint,
 			struct xfs_dquot **, struct xfs_dquot **);
 typedef void	(*xfs_dqvopcreate_t)(struct xfs_trans *, struct xfs_inode *,
 			struct xfs_dquot *, struct xfs_dquot *);
@@ -185,8 +185,8 @@
 	(*(mp)->m_qm_ops.xfs_dqdetach)(ip)
 #define XFS_QM_DQPURGEALL(mp, fl) \
 	(*(mp)->m_qm_ops.xfs_dqpurgeall)(mp, fl)
-#define XFS_QM_DQVOPALLOC(mp, ip, uid, gid, fl, dq1, dq2) \
-	(*(mp)->m_qm_ops.xfs_dqvopalloc)(mp, ip, uid, gid, fl, dq1, dq2)
+#define XFS_QM_DQVOPALLOC(mp, ip, uid, gid, prid, fl, dq1, dq2) \
+	(*(mp)->m_qm_ops.xfs_dqvopalloc)(mp, ip, uid, gid, prid, fl, dq1, dq2)
 #define XFS_QM_DQVOPCREATE(mp, tp, ip, dq1, dq2) \
 	(*(mp)->m_qm_ops.xfs_dqvopcreate)(tp, ip, dq1, dq2)
 #define XFS_QM_DQVOPRENAME(mp, ip) \
@@ -544,7 +544,6 @@
 extern int	xfs_mountfs(struct vfs *, xfs_mount_t *mp, int);
 
 extern int	xfs_unmountfs(xfs_mount_t *, struct cred *);
-extern void	xfs_unmountfs_wait(xfs_mount_t *);
 extern void	xfs_unmountfs_close(xfs_mount_t *, struct cred *);
 extern int	xfs_unmountfs_writesb(xfs_mount_t *);
 extern int	xfs_unmount_flush(xfs_mount_t *, int);
diff --git a/fs/xfs/xfs_quota.h b/fs/xfs/xfs_quota.h
index 703ec4e..7134576 100644
--- a/fs/xfs/xfs_quota.h
+++ b/fs/xfs/xfs_quota.h
@@ -96,7 +96,7 @@
  * flags for q_flags field in the dquot.
  */
 #define XFS_DQ_USER		0x0001		/* a user quota */
-/* #define XFS_DQ_PROJ		0x0002		-- project quota (IRIX) */
+#define XFS_DQ_PROJ		0x0002		/* project quota */
 #define XFS_DQ_GROUP		0x0004		/* a group quota */
 #define XFS_DQ_FLOCKED		0x0008		/* flush lock taken */
 #define XFS_DQ_DIRTY		0x0010		/* dquot is dirty */
@@ -104,6 +104,8 @@
 #define XFS_DQ_INACTIVE		0x0040		/* dq off mplist & hashlist */
 #define XFS_DQ_MARKER		0x0080		/* sentinel */
 
+#define XFS_DQ_ALLTYPES		(XFS_DQ_USER|XFS_DQ_PROJ|XFS_DQ_GROUP)
+
 /*
  * In the worst case, when both user and group quotas are on,
  * we can have a max of three dquots changing in a single transaction.
@@ -124,7 +126,7 @@
 typedef struct xfs_dq_logformat {
 	__uint16_t		qlf_type;      /* dquot log item type */
 	__uint16_t		qlf_size;      /* size of this item */
-	xfs_dqid_t		qlf_id;	       /* usr/grp id number : 32 bits */
+	xfs_dqid_t		qlf_id;	       /* usr/grp/proj id : 32 bits */
 	__int64_t		qlf_blkno;     /* blkno of dquot buffer */
 	__int32_t		qlf_len;       /* len of dquot buffer */
 	__uint32_t		qlf_boffset;   /* off of dquot in buffer */
@@ -152,9 +154,9 @@
 #define XFS_UQUOTA_ACCT	0x0001  /* user quota accounting ON */
 #define XFS_UQUOTA_ENFD	0x0002  /* user quota limits enforced */
 #define XFS_UQUOTA_CHKD	0x0004  /* quotacheck run on usr quotas */
-#define XFS_PQUOTA_ACCT	0x0008  /* (IRIX) project quota accounting ON */
-#define XFS_GQUOTA_ENFD	0x0010  /* group quota limits enforced */
-#define XFS_GQUOTA_CHKD	0x0020  /* quotacheck run on grp quotas */
+#define XFS_PQUOTA_ACCT	0x0008  /* project quota accounting ON */
+#define XFS_OQUOTA_ENFD	0x0010  /* other (grp/prj) quota limits enforced */
+#define XFS_OQUOTA_CHKD	0x0020  /* quotacheck run on other (grp/prj) quotas */
 #define XFS_GQUOTA_ACCT	0x0040  /* group quota accounting ON */
 
 /*
@@ -162,17 +164,22 @@
  * are in the process of getting turned off. These flags are in m_qflags but
  * never in sb_qflags.
  */
-#define XFS_UQUOTA_ACTIVE	0x0080  /* uquotas are being turned off */
-#define XFS_GQUOTA_ACTIVE	0x0100  /* gquotas are being turned off */
+#define XFS_UQUOTA_ACTIVE	0x0100  /* uquotas are being turned off */
+#define XFS_PQUOTA_ACTIVE	0x0200  /* pquotas are being turned off */
+#define XFS_GQUOTA_ACTIVE	0x0400  /* gquotas are being turned off */
 
 /*
  * Checking XFS_IS_*QUOTA_ON() while holding any inode lock guarantees
  * quota will be not be switched off as long as that inode lock is held.
  */
 #define XFS_IS_QUOTA_ON(mp)	((mp)->m_qflags & (XFS_UQUOTA_ACTIVE | \
-						   XFS_GQUOTA_ACTIVE))
+						   XFS_GQUOTA_ACTIVE | \
+						   XFS_PQUOTA_ACTIVE))
+#define XFS_IS_OQUOTA_ON(mp)	((mp)->m_qflags & (XFS_GQUOTA_ACTIVE | \
+						   XFS_PQUOTA_ACTIVE))
 #define XFS_IS_UQUOTA_ON(mp)	((mp)->m_qflags & XFS_UQUOTA_ACTIVE)
 #define XFS_IS_GQUOTA_ON(mp)	((mp)->m_qflags & XFS_GQUOTA_ACTIVE)
+#define XFS_IS_PQUOTA_ON(mp)	((mp)->m_qflags & XFS_PQUOTA_ACTIVE)
 
 /*
  * Flags to tell various functions what to do. Not all of these are meaningful
@@ -182,7 +189,7 @@
 #define XFS_QMOPT_DQLOCK	0x0000001 /* dqlock */
 #define XFS_QMOPT_DQALLOC	0x0000002 /* alloc dquot ondisk if needed */
 #define XFS_QMOPT_UQUOTA	0x0000004 /* user dquot requested */
-#define XFS_QMOPT_GQUOTA	0x0000008 /* group dquot requested */
+#define XFS_QMOPT_PQUOTA	0x0000008 /* project dquot requested */
 #define XFS_QMOPT_FORCE_RES	0x0000010 /* ignore quota limits */
 #define XFS_QMOPT_DQSUSER	0x0000020 /* don't cache super users dquot */
 #define XFS_QMOPT_SBVERSION	0x0000040 /* change superblock version num */
@@ -192,6 +199,7 @@
 #define XFS_QMOPT_DOWARN        0x0000400 /* increase warning cnt if necessary */
 #define XFS_QMOPT_ILOCKED	0x0000800 /* inode is already locked (excl) */
 #define XFS_QMOPT_DQREPAIR	0x0001000 /* repair dquot, if damaged. */
+#define XFS_QMOPT_GQUOTA	0x0002000 /* group dquot requested */
 
 /*
  * flags to xfs_trans_mod_dquot to indicate which field needs to be
@@ -231,7 +239,8 @@
 #define XFS_TRANS_DQ_DELRTBCOUNT XFS_QMOPT_DELRTBCOUNT
 
 
-#define XFS_QMOPT_QUOTALL	(XFS_QMOPT_UQUOTA|XFS_QMOPT_GQUOTA)
+#define XFS_QMOPT_QUOTALL	\
+		(XFS_QMOPT_UQUOTA | XFS_QMOPT_PQUOTA | XFS_QMOPT_GQUOTA)
 #define XFS_QMOPT_RESBLK_MASK	(XFS_QMOPT_RES_REGBLKS | XFS_QMOPT_RES_RTBLKS)
 
 #ifdef __KERNEL__
@@ -246,21 +255,33 @@
  */
 #define XFS_NOT_DQATTACHED(mp, ip) ((XFS_IS_UQUOTA_ON(mp) &&\
 				     (ip)->i_udquot == NULL) || \
-				    (XFS_IS_GQUOTA_ON(mp) && \
+				    (XFS_IS_OQUOTA_ON(mp) && \
 				     (ip)->i_gdquot == NULL))
 
-#define XFS_QM_NEED_QUOTACHECK(mp) ((XFS_IS_UQUOTA_ON(mp) && \
-				     (mp->m_sb.sb_qflags & \
-				      XFS_UQUOTA_CHKD) == 0) || \
-				    (XFS_IS_GQUOTA_ON(mp) && \
-				     (mp->m_sb.sb_qflags & \
-				      XFS_GQUOTA_CHKD) == 0))
+#define XFS_QM_NEED_QUOTACHECK(mp) \
+	((XFS_IS_UQUOTA_ON(mp) && \
+		(mp->m_sb.sb_qflags & XFS_UQUOTA_CHKD) == 0) || \
+	 (XFS_IS_GQUOTA_ON(mp) && \
+		((mp->m_sb.sb_qflags & XFS_OQUOTA_CHKD) == 0 || \
+		 (mp->m_sb.sb_qflags & XFS_PQUOTA_ACCT))) || \
+	 (XFS_IS_PQUOTA_ON(mp) && \
+		((mp->m_sb.sb_qflags & XFS_OQUOTA_CHKD) == 0 || \
+		 (mp->m_sb.sb_qflags & XFS_GQUOTA_ACCT))))
+
+#define XFS_MOUNT_QUOTA_SET1	(XFS_UQUOTA_ACCT|XFS_UQUOTA_ENFD|\
+				 XFS_UQUOTA_CHKD|XFS_PQUOTA_ACCT|\
+				 XFS_OQUOTA_ENFD|XFS_OQUOTA_CHKD)
+
+#define XFS_MOUNT_QUOTA_SET2	(XFS_UQUOTA_ACCT|XFS_UQUOTA_ENFD|\
+				 XFS_UQUOTA_CHKD|XFS_GQUOTA_ACCT|\
+				 XFS_OQUOTA_ENFD|XFS_OQUOTA_CHKD)
 
 #define XFS_MOUNT_QUOTA_ALL	(XFS_UQUOTA_ACCT|XFS_UQUOTA_ENFD|\
-				 XFS_UQUOTA_CHKD|XFS_GQUOTA_ACCT|\
-				 XFS_GQUOTA_ENFD|XFS_GQUOTA_CHKD)
+				 XFS_UQUOTA_CHKD|XFS_PQUOTA_ACCT|\
+				 XFS_OQUOTA_ENFD|XFS_OQUOTA_CHKD|\
+				 XFS_GQUOTA_ACCT)
 #define XFS_MOUNT_QUOTA_MASK	(XFS_MOUNT_QUOTA_ALL | XFS_UQUOTA_ACTIVE | \
-				 XFS_GQUOTA_ACTIVE)
+				 XFS_GQUOTA_ACTIVE | XFS_PQUOTA_ACTIVE)
 
 
 /*
@@ -331,15 +352,8 @@
 #define XFS_TRANS_UNRESERVE_AND_MOD_DQUOTS(mp, tp) \
 	XFS_DQTRXOP_VOID(mp, tp, qo_unreserve_and_mod_dquots)
 
-#define XFS_TRANS_RESERVE_BLKQUOTA(mp, tp, ip, nblks) \
-	XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, tp, ip, nblks, 0, \
-				XFS_QMOPT_RES_REGBLKS)
-#define XFS_TRANS_RESERVE_BLKQUOTA_FORCE(mp, tp, ip, nblks) \
-	XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, tp, ip, nblks, 0, \
-				XFS_QMOPT_RES_REGBLKS | XFS_QMOPT_FORCE_RES)
-#define XFS_TRANS_UNRESERVE_BLKQUOTA(mp, tp, ip, nblks) \
-	XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, tp, ip, -(nblks), 0, \
-				XFS_QMOPT_RES_REGBLKS)
+#define XFS_TRANS_UNRESERVE_QUOTA_NBLKS(mp, tp, ip, nblks, ninos, flags) \
+	XFS_TRANS_RESERVE_QUOTA_NBLKS(mp, tp, ip, -(nblks), -(ninos), flags)
 #define XFS_TRANS_RESERVE_QUOTA(mp, tp, ud, gd, nb, ni, f) \
 	XFS_TRANS_RESERVE_QUOTA_BYDQUOTS(mp, tp, ud, gd, nb, ni, \
 				f | XFS_QMOPT_RES_REGBLKS)
diff --git a/fs/xfs/xfs_rename.c b/fs/xfs/xfs_rename.c
index cb13f9a..23b48ac 100644
--- a/fs/xfs/xfs_rename.c
+++ b/fs/xfs/xfs_rename.c
@@ -234,9 +234,6 @@
 	return 0;
 }
 
-
-int rename_which_error_return = 0;
-
 /*
  * xfs_rename
  */
@@ -316,7 +313,6 @@
 			&num_inodes);
 
 	if (error) {
-		rename_which_error_return = __LINE__;
 		/*
 		 * We have nothing locked, no inode references, and
 		 * no transaction, so just get out.
@@ -332,7 +328,6 @@
 		 */
 		if (target_ip == NULL && (src_dp != target_dp) &&
 		    target_dp->i_d.di_nlink >= XFS_MAXLINK) {
-			rename_which_error_return = __LINE__;
 			error = XFS_ERROR(EMLINK);
 			xfs_rename_unlock4(inodes, XFS_ILOCK_SHARED);
 			goto rele_return;
@@ -359,7 +354,6 @@
 				XFS_TRANS_PERM_LOG_RES, XFS_RENAME_LOG_COUNT);
 	}
 	if (error) {
-		rename_which_error_return = __LINE__;
 		xfs_trans_cancel(tp, 0);
 		goto rele_return;
 	}
@@ -369,7 +363,6 @@
 	 */
 	if ((error = XFS_QM_DQVOPRENAME(mp, inodes))) {
 		xfs_trans_cancel(tp, cancel_flags);
-		rename_which_error_return = __LINE__;
 		goto rele_return;
 	}
 
@@ -413,7 +406,6 @@
 		if (spaceres == 0 &&
 		    (error = XFS_DIR_CANENTER(mp, tp, target_dp, target_name,
 				target_namelen))) {
-			rename_which_error_return = __LINE__;
 			goto error_return;
 		}
 		/*
@@ -425,11 +417,9 @@
 					   target_namelen, src_ip->i_ino,
 					   &first_block, &free_list, spaceres);
 		if (error == ENOSPC) {
-			rename_which_error_return = __LINE__;
 			goto error_return;
 		}
 		if (error) {
-			rename_which_error_return = __LINE__;
 			goto abort_return;
 		}
 		xfs_ichgtime(target_dp, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG);
@@ -437,7 +427,6 @@
 		if (new_parent && src_is_directory) {
 			error = xfs_bumplink(tp, target_dp);
 			if (error) {
-				rename_which_error_return = __LINE__;
 				goto abort_return;
 			}
 		}
@@ -455,7 +444,6 @@
 			if (!(XFS_DIR_ISEMPTY(target_ip->i_mount, target_ip)) ||
 			    (target_ip->i_d.di_nlink > 2)) {
 				error = XFS_ERROR(EEXIST);
-				rename_which_error_return = __LINE__;
 				goto error_return;
 			}
 		}
@@ -473,7 +461,6 @@
 			target_namelen, src_ip->i_ino, &first_block,
 			&free_list, spaceres);
 		if (error) {
-			rename_which_error_return = __LINE__;
 			goto abort_return;
 		}
 		xfs_ichgtime(target_dp, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG);
@@ -484,7 +471,6 @@
 		 */
 		error = xfs_droplink(tp, target_ip);
 		if (error) {
-			rename_which_error_return = __LINE__;
 			goto abort_return;
 		}
 		target_ip_dropped = 1;
@@ -495,7 +481,6 @@
 			 */
 			error = xfs_droplink(tp, target_ip);
 			if (error) {
-				rename_which_error_return = __LINE__;
 				goto abort_return;
 			}
 		}
@@ -519,7 +504,6 @@
 					&free_list, spaceres);
 		ASSERT(error != EEXIST);
 		if (error) {
-			rename_which_error_return = __LINE__;
 			goto abort_return;
 		}
 		xfs_ichgtime(src_ip, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG);
@@ -550,7 +534,6 @@
 		 */
 		error = xfs_droplink(tp, src_dp);
 		if (error) {
-			rename_which_error_return = __LINE__;
 			goto abort_return;
 		}
 	}
@@ -558,7 +541,6 @@
 	error = XFS_DIR_REMOVENAME(mp, tp, src_dp, src_name, src_namelen,
 			src_ip->i_ino, &first_block, &free_list, spaceres);
 	if (error) {
-		rename_which_error_return = __LINE__;
 		goto abort_return;
 	}
 	xfs_ichgtime(src_dp, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG);
diff --git a/fs/xfs/xfs_trans.c b/fs/xfs/xfs_trans.c
index 3db0e22..06dfca5 100644
--- a/fs/xfs/xfs_trans.c
+++ b/fs/xfs/xfs_trans.c
@@ -332,25 +332,6 @@
 
 
 /*
- * This is called to set the a callback to be called when the given
- * transaction is committed to disk.  The transaction pointer and the
- * argument pointer will be passed to the callback routine.
- *
- * Only one callback can be associated with any single transaction.
- */
-void
-xfs_trans_callback(
-	xfs_trans_t		*tp,
-	xfs_trans_callback_t	callback,
-	void			*arg)
-{
-	ASSERT(tp->t_callback == NULL);
-	tp->t_callback = callback;
-	tp->t_callarg = arg;
-}
-
-
-/*
  * Record the indicated change to the given field for application
  * to the file system's superblock when the transaction commits.
  * For now, just store the change in the transaction structure.
@@ -551,7 +532,7 @@
  *
  * This is done efficiently with a single call to xfs_mod_incore_sb_batch().
  */
-void
+STATIC void
 xfs_trans_unreserve_and_mod_sb(
 	xfs_trans_t	*tp)
 {
diff --git a/fs/xfs/xfs_trans.h b/fs/xfs/xfs_trans.h
index bd37ccb..ec541d6 100644
--- a/fs/xfs/xfs_trans.h
+++ b/fs/xfs/xfs_trans.h
@@ -987,8 +987,6 @@
 xfs_trans_t	*xfs_trans_dup(xfs_trans_t *);
 int		xfs_trans_reserve(xfs_trans_t *, uint, uint, uint,
 				  uint, uint);
-void		xfs_trans_callback(xfs_trans_t *,
-				   void (*)(xfs_trans_t *, void *), void *);
 void		xfs_trans_mod_sb(xfs_trans_t *, uint, long);
 struct xfs_buf	*xfs_trans_get_buf(xfs_trans_t *, struct xfs_buftarg *, xfs_daddr_t,
 				   int, uint);
@@ -1010,7 +1008,6 @@
 			       xfs_ino_t , uint, uint, struct xfs_inode **);
 void		xfs_trans_ijoin(xfs_trans_t *, struct xfs_inode *, uint);
 void		xfs_trans_ihold(xfs_trans_t *, struct xfs_inode *);
-void		xfs_trans_ihold_release(xfs_trans_t *, struct xfs_inode *);
 void		xfs_trans_log_buf(xfs_trans_t *, struct xfs_buf *, uint, uint);
 void		xfs_trans_log_inode(xfs_trans_t *, struct xfs_inode *, uint);
 struct xfs_efi_log_item	*xfs_trans_get_efi(xfs_trans_t *, uint);
diff --git a/fs/xfs/xfs_trans_buf.c b/fs/xfs/xfs_trans_buf.c
index a9682b9..144da7a 100644
--- a/fs/xfs/xfs_trans_buf.c
+++ b/fs/xfs/xfs_trans_buf.c
@@ -976,6 +976,7 @@
 	ASSERT(XFS_BUF_FSPRIVATE2(bp, xfs_trans_t *) == tp);
 	ASSERT(XFS_BUF_FSPRIVATE(bp, void *) != NULL);
 	ASSERT(type == XFS_BLI_UDQUOT_BUF ||
+	       type == XFS_BLI_PDQUOT_BUF ||
 	       type == XFS_BLI_GDQUOT_BUF);
 
 	bip = XFS_BUF_FSPRIVATE(bp, xfs_buf_log_item_t *);
diff --git a/fs/xfs/xfs_trans_inode.c b/fs/xfs/xfs_trans_inode.c
index e2c3706..7e7631c 100644
--- a/fs/xfs/xfs_trans_inode.c
+++ b/fs/xfs/xfs_trans_inode.c
@@ -253,24 +253,6 @@
 	ip->i_itemp->ili_flags |= XFS_ILI_HOLD;
 }
 
-/*
- * Cancel the previous inode hold request made on this inode
- * for this transaction.
- */
-/*ARGSUSED*/
-void
-xfs_trans_ihold_release(
-	xfs_trans_t	*tp,
-	xfs_inode_t	*ip)
-{
-	ASSERT(ip->i_transp == tp);
-	ASSERT(ip->i_itemp != NULL);
-	ASSERT(ismrlocked(&ip->i_lock, MR_UPDATE));
-	ASSERT(ip->i_itemp->ili_flags & XFS_ILI_HOLD);
-
-	ip->i_itemp->ili_flags &= ~XFS_ILI_HOLD;
-}
-
 
 /*
  * This is called to mark the fields indicated in fieldmask as needing
diff --git a/fs/xfs/xfs_types.h b/fs/xfs/xfs_types.h
index e4bf711..16f5371 100644
--- a/fs/xfs/xfs_types.h
+++ b/fs/xfs/xfs_types.h
@@ -55,7 +55,7 @@
 typedef unsigned long long int	__uint64_t;
 
 typedef enum { B_FALSE,B_TRUE }	boolean_t;
-typedef __int64_t		prid_t;		/* project ID */
+typedef __uint32_t		prid_t;		/* project ID */
 typedef __uint32_t		inst_t;		/* an instruction */
 
 typedef __s64			xfs_off_t;	/* <file offset> type */
diff --git a/fs/xfs/xfs_utils.c b/fs/xfs/xfs_utils.c
index d1f8146..11351f0 100644
--- a/fs/xfs/xfs_utils.c
+++ b/fs/xfs/xfs_utils.c
@@ -428,7 +428,7 @@
 		if (ip->i_ino != mp->m_sb.sb_uquotino)
 			ASSERT(ip->i_udquot);
 	}
-	if (XFS_IS_GQUOTA_ON(mp)) {
+	if (XFS_IS_OQUOTA_ON(mp)) {
 		if (ip->i_ino != mp->m_sb.sb_gquotino)
 			ASSERT(ip->i_gdquot);
 	}
diff --git a/fs/xfs/xfs_vfsops.c b/fs/xfs/xfs_vfsops.c
index b537366..42bcc02 100644
--- a/fs/xfs/xfs_vfsops.c
+++ b/fs/xfs/xfs_vfsops.c
@@ -368,16 +368,6 @@
 	}
 
 	/*
-	 * disallow mount attempts with (IRIX) project quota enabled
-	 */
-	if (XFS_SB_VERSION_HASQUOTA(&mp->m_sb) &&
-	    (mp->m_sb.sb_qflags & XFS_PQUOTA_ACCT)) {
-		cmn_err(CE_WARN,
-	"XFS: cannot mount a filesystem with IRIX project quota enabled");
-		return XFS_ERROR(ENOSYS);
-	}
-
-	/*
 	 * check for shared mount.
 	 */
 	if (ap->flags & XFSMNT_SHARED) {
@@ -622,7 +612,34 @@
 	return XFS_ERROR(error);
 }
 
-#define REMOUNT_READONLY_FLAGS	(SYNC_REMOUNT|SYNC_ATTR|SYNC_WAIT)
+STATIC int
+xfs_quiesce_fs(
+	xfs_mount_t		*mp)
+{
+	int			count = 0, pincount;
+		
+	xfs_refcache_purge_mp(mp);
+	xfs_flush_buftarg(mp->m_ddev_targp, 0);
+	xfs_finish_reclaim_all(mp, 0);
+
+	/* This loop must run at least twice.
+	 * The first instance of the loop will flush
+	 * most meta data but that will generate more
+	 * meta data (typically directory updates).
+	 * Which then must be flushed and logged before
+	 * we can write the unmount record.
+	 */ 
+	do {
+		xfs_syncsub(mp, SYNC_REMOUNT|SYNC_ATTR|SYNC_WAIT, 0, NULL);
+		pincount = xfs_flush_buftarg(mp->m_ddev_targp, 1);
+		if (!pincount) {
+			delay(50);
+			count++;
+		}
+	} while (count < 2);
+
+	return 0;
+}
 
 STATIC int
 xfs_mntupdate(
@@ -632,8 +649,7 @@
 {
 	struct vfs	*vfsp = bhvtovfs(bdp);
 	xfs_mount_t	*mp = XFS_BHVTOM(bdp);
-	int		pincount, error;
-	int		count = 0;
+	int		error;
 
 	if (args->flags & XFSMNT_NOATIME)
 		mp->m_flags |= XFS_MOUNT_NOATIME;
@@ -645,25 +661,7 @@
 	}
 
 	if (*flags & MS_RDONLY) {
-		xfs_refcache_purge_mp(mp);
-		xfs_flush_buftarg(mp->m_ddev_targp, 0);
-		xfs_finish_reclaim_all(mp, 0);
-
-		/* This loop must run at least twice.
-		 * The first instance of the loop will flush
-		 * most meta data but that will generate more
-		 * meta data (typically directory updates).
-		 * Which then must be flushed and logged before
-		 * we can write the unmount record.
-		 */ 
-		do {
-			VFS_SYNC(vfsp, REMOUNT_READONLY_FLAGS, NULL, error);
-			pincount = xfs_flush_buftarg(mp->m_ddev_targp, 1);
-			if (!pincount) {
-				delay(50);
-				count++;
-			}
-		} while (count < 2);
+		xfs_quiesce_fs(mp);
 
 		/* Ok now write out an unmount record */
 		xfs_log_unmount_write(mp);
@@ -879,10 +877,12 @@
 	int		flags,
 	cred_t		*credp)
 {
-	xfs_mount_t	*mp;
+	xfs_mount_t	*mp = XFS_BHVTOM(bdp);
 
-	mp = XFS_BHVTOM(bdp);
-	return (xfs_syncsub(mp, flags, 0, NULL));
+	if (unlikely(flags == SYNC_QUIESCE))
+		return xfs_quiesce_fs(mp);
+	else
+		return xfs_syncsub(mp, flags, 0, NULL);
 }
 
 /*
@@ -1681,7 +1681,7 @@
 	return simple_strtoul(cp, endp, base) << shift_left_factor;
 }
 
-int
+STATIC int
 xfs_parseargs(
 	struct bhv_desc		*bhv,
 	char			*options,
@@ -1867,7 +1867,7 @@
 	return 0;
 }
 
-int
+STATIC int
 xfs_showargs(
 	struct bhv_desc		*bhv,
 	struct seq_file		*m)
diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c
index 25a5266..1377c86 100644
--- a/fs/xfs/xfs_vnodeops.c
+++ b/fs/xfs/xfs_vnodeops.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000-2004 Silicon Graphics, Inc.  All Rights Reserved.
+ * Copyright (c) 2000-2005 Silicon Graphics, Inc.  All Rights Reserved.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms of version 2 of the GNU General Public License as
@@ -351,21 +351,28 @@
 	 * If the IDs do change before we take the ilock, we're covered
 	 * because the i_*dquot fields will get updated anyway.
 	 */
-	if (XFS_IS_QUOTA_ON(mp) && (mask & (XFS_AT_UID|XFS_AT_GID))) {
+	if (XFS_IS_QUOTA_ON(mp) &&
+	    (mask & (XFS_AT_UID|XFS_AT_GID|XFS_AT_PROJID))) {
 		uint	qflags = 0;
 
-		if (mask & XFS_AT_UID) {
+		if ((mask & XFS_AT_UID) && XFS_IS_UQUOTA_ON(mp)) {
 			uid = vap->va_uid;
 			qflags |= XFS_QMOPT_UQUOTA;
 		} else {
 			uid = ip->i_d.di_uid;
 		}
-		if (mask & XFS_AT_GID) {
+		if ((mask & XFS_AT_GID) && XFS_IS_GQUOTA_ON(mp)) {
 			gid = vap->va_gid;
 			qflags |= XFS_QMOPT_GQUOTA;
 		}  else {
 			gid = ip->i_d.di_gid;
 		}
+		if ((mask & XFS_AT_PROJID) && XFS_IS_PQUOTA_ON(mp)) {
+			projid = vap->va_projid;
+			qflags |= XFS_QMOPT_PQUOTA;
+		}  else {
+			projid = ip->i_d.di_projid;
+		}
 		/*
 		 * We take a reference when we initialize udqp and gdqp,
 		 * so it is important that we never blindly double trip on
@@ -373,7 +380,8 @@
 		 */
 		ASSERT(udqp == NULL);
 		ASSERT(gdqp == NULL);
-		code = XFS_QM_DQVOPALLOC(mp, ip, uid,gid, qflags, &udqp, &gdqp);
+		code = XFS_QM_DQVOPALLOC(mp, ip, uid, gid, projid, qflags,
+					 &udqp, &gdqp);
 		if (code)
 			return (code);
 	}
@@ -499,8 +507,6 @@
 		 * that the group ID supplied to the chown() function
 		 * shall be equal to either the group ID or one of the
 		 * supplementary group IDs of the calling process.
-		 *
-		 * XXX: How does restricted_chown affect projid?
 		 */
 		if (restricted_chown &&
 		    (iuid != uid || (igid != gid &&
@@ -510,10 +516,11 @@
 			goto error_return;
 		}
 		/*
-		 * Do a quota reservation only if uid or gid is actually
+		 * Do a quota reservation only if uid/projid/gid is actually
 		 * going to change.
 		 */
 		if ((XFS_IS_UQUOTA_ON(mp) && iuid != uid) ||
+		    (XFS_IS_PQUOTA_ON(mp) && iprojid != projid) ||
 		    (XFS_IS_GQUOTA_ON(mp) && igid != gid)) {
 			ASSERT(tp);
 			code = XFS_QM_DQVOPCHOWNRESV(mp, tp, ip, udqp, gdqp,
@@ -774,6 +781,7 @@
 		}
 		if (igid != gid) {
 			if (XFS_IS_GQUOTA_ON(mp)) {
+				ASSERT(!XFS_IS_PQUOTA_ON(mp));
 				ASSERT(mask & XFS_AT_GID);
 				ASSERT(gdqp);
 				olddquot2 = XFS_QM_DQVOPCHOWN(mp, tp, ip,
@@ -782,6 +790,13 @@
 			ip->i_d.di_gid = gid;
 		}
 		if (iprojid != projid) {
+			if (XFS_IS_PQUOTA_ON(mp)) {
+				ASSERT(!XFS_IS_GQUOTA_ON(mp));
+				ASSERT(mask & XFS_AT_PROJID);
+				ASSERT(gdqp);
+				olddquot2 = XFS_QM_DQVOPCHOWN(mp, tp, ip,
+							&ip->i_gdquot, gdqp);
+			}
 			ip->i_d.di_projid = projid;
 			/*
 			 * We may have to rev the inode as well as
@@ -843,6 +858,8 @@
 				di_flags |= XFS_DIFLAG_NOATIME;
 			if (vap->va_xflags & XFS_XFLAG_NODUMP)
 				di_flags |= XFS_DIFLAG_NODUMP;
+			if (vap->va_xflags & XFS_XFLAG_PROJINHERIT)
+				di_flags |= XFS_DIFLAG_PROJINHERIT;
 			if ((ip->i_d.di_mode & S_IFMT) == S_IFDIR) {
 				if (vap->va_xflags & XFS_XFLAG_RTINHERIT)
 					di_flags |= XFS_DIFLAG_RTINHERIT;
@@ -1898,7 +1915,9 @@
 	/* Return through std_return after this point. */
 
 	udqp = gdqp = NULL;
-	if (vap->va_mask & XFS_AT_PROJID)
+	if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT)
+		prid = dp->i_d.di_projid;
+	else if (vap->va_mask & XFS_AT_PROJID)
 		prid = (xfs_prid_t)vap->va_projid;
 	else
 		prid = (xfs_prid_t)dfltprid;
@@ -1907,7 +1926,7 @@
 	 * Make sure that we have allocated dquot(s) on disk.
 	 */
 	error = XFS_QM_DQVOPALLOC(mp, dp,
-			current_fsuid(credp), current_fsgid(credp),
+			current_fsuid(credp), current_fsgid(credp), prid,
 			XFS_QMOPT_QUOTALL|XFS_QMOPT_INHERIT, &udqp, &gdqp);
 	if (error)
 		goto std_return;
@@ -2604,17 +2623,7 @@
 	if (src_vp->v_type == VDIR)
 		return XFS_ERROR(EPERM);
 
-	/*
-	 * For now, manually find the XFS behavior descriptor for
-	 * the source vnode.  If it doesn't exist then something
-	 * is wrong and we should just return an error.
-	 * Eventually we need to figure out how link is going to
-	 * work in the face of stacked vnodes.
-	 */
 	src_bdp = vn_bhv_lookup_unlocked(VN_BHV_HEAD(src_vp), &xfs_vnodeops);
-	if (src_bdp == NULL) {
-		return XFS_ERROR(EXDEV);
-	}
 	sip = XFS_BHVTOI(src_bdp);
 	tdp = XFS_BHVTOI(target_dir_bdp);
 	mp = tdp->i_mount;
@@ -2681,6 +2690,17 @@
 		goto error_return;
 	}
 
+	/*
+	 * If we are using project inheritance, we only allow hard link
+	 * creation in our tree when the project IDs are the same; else
+	 * the tree quota mechanism could be circumvented.
+	 */
+	if (unlikely((tdp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) &&
+		     (tdp->i_d.di_projid != sip->i_d.di_projid))) {
+		error = XFS_ERROR(EPERM);
+		goto error_return;
+	}
+
 	if (resblks == 0 &&
 	    (error = XFS_DIR_CANENTER(mp, tp, tdp, target_name,
 			target_namelen)))
@@ -2803,7 +2823,9 @@
 
 	mp = dp->i_mount;
 	udqp = gdqp = NULL;
-	if (vap->va_mask & XFS_AT_PROJID)
+	if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT)
+		prid = dp->i_d.di_projid;
+	else if (vap->va_mask & XFS_AT_PROJID)
 		prid = (xfs_prid_t)vap->va_projid;
 	else
 		prid = (xfs_prid_t)dfltprid;
@@ -2812,7 +2834,7 @@
 	 * Make sure that we have allocated dquot(s) on disk.
 	 */
 	error = XFS_QM_DQVOPALLOC(mp, dp,
-			current_fsuid(credp), current_fsgid(credp),
+			current_fsuid(credp), current_fsgid(credp), prid,
 			XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp);
 	if (error)
 		goto std_return;
@@ -3357,7 +3379,9 @@
 	/* Return through std_return after this point. */
 
 	udqp = gdqp = NULL;
-	if (vap->va_mask & XFS_AT_PROJID)
+	if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT)
+		prid = dp->i_d.di_projid;
+	else if (vap->va_mask & XFS_AT_PROJID)
 		prid = (xfs_prid_t)vap->va_projid;
 	else
 		prid = (xfs_prid_t)dfltprid;
@@ -3366,7 +3390,7 @@
 	 * Make sure that we have allocated dquot(s) on disk.
 	 */
 	error = XFS_QM_DQVOPALLOC(mp, dp,
-			current_fsuid(credp), current_fsgid(credp),
+			current_fsuid(credp), current_fsgid(credp), prid,
 			XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp);
 	if (error)
 		goto std_return;
@@ -4028,7 +4052,7 @@
  *      errno on error
  *
  */
-int
+STATIC int
 xfs_alloc_file_space(
 	xfs_inode_t		*ip,
 	xfs_off_t		offset,
@@ -4151,9 +4175,8 @@
 			break;
 		}
 		xfs_ilock(ip, XFS_ILOCK_EXCL);
-		error = XFS_TRANS_RESERVE_QUOTA_BYDQUOTS(mp, tp,
-				ip->i_udquot, ip->i_gdquot, resblks, 0, rt ?
-				XFS_QMOPT_RES_RTBLKS : XFS_QMOPT_RES_REGBLKS);
+		error = XFS_TRANS_RESERVE_QUOTA(mp, tp,
+				ip->i_udquot, ip->i_gdquot, resblks, 0, 0);
 		if (error)
 			goto error1;
 
@@ -4305,6 +4328,7 @@
 	xfs_off_t		len,
 	int			attr_flags)
 {
+	vnode_t			*vp;
 	int			committed;
 	int			done;
 	xfs_off_t		end_dmi_offset;
@@ -4325,9 +4349,11 @@
 	xfs_trans_t		*tp;
 	int			need_iolock = 1;
 
-	vn_trace_entry(XFS_ITOV(ip), __FUNCTION__, (inst_t *)__return_address);
+	vp = XFS_ITOV(ip);
 	mp = ip->i_mount;
 
+	vn_trace_entry(vp, __FUNCTION__, (inst_t *)__return_address);
+
 	if ((error = XFS_QM_DQATTACH(mp, ip, 0)))
 		return error;
 
@@ -4344,7 +4370,7 @@
 	    DM_EVENT_ENABLED(XFS_MTOVFS(mp), ip, DM_EVENT_WRITE)) {
 		if (end_dmi_offset > ip->i_d.di_size)
 			end_dmi_offset = ip->i_d.di_size;
-		error = XFS_SEND_DATA(mp, DM_EVENT_WRITE, XFS_ITOV(ip),
+		error = XFS_SEND_DATA(mp, DM_EVENT_WRITE, vp,
 				offset, end_dmi_offset - offset,
 				AT_DELAY_FLAG(attr_flags), NULL);
 		if (error)
@@ -4363,7 +4389,14 @@
 	ioffset = offset & ~(rounding - 1);
 	if (ilen & (rounding - 1))
 		ilen = (ilen + rounding) & ~(rounding - 1);
-	xfs_inval_cached_pages(XFS_ITOV(ip), &(ip->i_iocore), ioffset, 0, 0);
+
+	if (VN_CACHED(vp) != 0) {
+		xfs_inval_cached_trace(&ip->i_iocore, ioffset, -1,
+				ctooff(offtoct(ioffset)), -1);
+		VOP_FLUSHINVAL_PAGES(vp, ctooff(offtoct(ioffset)),
+				-1, FI_REMAPF_LOCKED);
+	}
+
 	/*
 	 * Need to zero the stuff we're not freeing, on disk.
 	 * If its a realtime file & can't use unwritten extents then we
diff --git a/include/asm-alpha/smp.h b/include/asm-alpha/smp.h
index cbc173a..9950706 100644
--- a/include/asm-alpha/smp.h
+++ b/include/asm-alpha/smp.h
@@ -43,7 +43,7 @@
 #define PROC_CHANGE_PENALTY     20
 
 #define hard_smp_processor_id()	__hard_smp_processor_id()
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id()	(current_thread_info()->cpu)
 
 extern cpumask_t cpu_present_mask;
 extern cpumask_t cpu_online_map;
diff --git a/include/asm-arm/smp.h b/include/asm-arm/smp.h
index bd44f89..6c6c60a 100644
--- a/include/asm-arm/smp.h
+++ b/include/asm-arm/smp.h
@@ -21,7 +21,7 @@
 # error "<asm-arm/smp.h> included in non-SMP build"
 #endif
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id() (current_thread_info()->cpu)
 
 extern cpumask_t cpu_present_mask;
 #define cpu_possible_map cpu_present_mask
diff --git a/include/asm-arm/system.h b/include/asm-arm/system.h
index 8405eb6..39dd700 100644
--- a/include/asm-arm/system.h
+++ b/include/asm-arm/system.h
@@ -308,7 +308,7 @@
 ({					\
 	unsigned long flags;		\
 	local_save_flags(flags);	\
-	flags & PSR_I_BIT;		\
+	(int)(flags & PSR_I_BIT);	\
 })
 
 #ifdef CONFIG_SMP
diff --git a/include/asm-generic/pgtable.h b/include/asm-generic/pgtable.h
index 1f4ec7b..f405935 100644
--- a/include/asm-generic/pgtable.h
+++ b/include/asm-generic/pgtable.h
@@ -125,6 +125,9 @@
 
 #ifndef __HAVE_ARCH_PAGE_TEST_AND_CLEAR_DIRTY
 #define page_test_and_clear_dirty(page) (0)
+#define pte_maybe_dirty(pte)		pte_dirty(pte)
+#else
+#define pte_maybe_dirty(pte)		(1)
 #endif
 
 #ifndef __HAVE_ARCH_PAGE_TEST_AND_CLEAR_YOUNG
diff --git a/include/asm-i386/page.h b/include/asm-i386/page.h
index ed13969..41400d3 100644
--- a/include/asm-i386/page.h
+++ b/include/asm-i386/page.h
@@ -68,6 +68,7 @@
 #define HPAGE_MASK	(~(HPAGE_SIZE - 1))
 #define HUGETLB_PAGE_ORDER	(HPAGE_SHIFT - PAGE_SHIFT)
 #define HAVE_ARCH_HUGETLB_UNMAPPED_AREA
+#define ARCH_HAS_HUGETLB_CLEAN_STALE_PGTABLE
 #endif
 
 #define pgd_val(x)	((x).pgd)
diff --git a/include/asm-i386/pgtable.h b/include/asm-i386/pgtable.h
index 8d60c2b..e9efe14 100644
--- a/include/asm-i386/pgtable.h
+++ b/include/asm-i386/pgtable.h
@@ -236,6 +236,7 @@
 static inline pte_t pte_mkdirty(pte_t pte)	{ (pte).pte_low |= _PAGE_DIRTY; return pte; }
 static inline pte_t pte_mkyoung(pte_t pte)	{ (pte).pte_low |= _PAGE_ACCESSED; return pte; }
 static inline pte_t pte_mkwrite(pte_t pte)	{ (pte).pte_low |= _PAGE_RW; return pte; }
+static inline pte_t pte_mkhuge(pte_t pte)	{ (pte).pte_low |= _PAGE_PRESENT | _PAGE_PSE; return pte; }
 
 #ifdef CONFIG_X86_PAE
 # include <asm/pgtable-3level.h>
@@ -275,7 +276,6 @@
  */
 
 #define mk_pte(page, pgprot)	pfn_pte(page_to_pfn(page), (pgprot))
-#define mk_pte_huge(entry) ((entry).pte_low |= _PAGE_PRESENT | _PAGE_PSE)
 
 static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
 {
diff --git a/include/asm-i386/smp.h b/include/asm-i386/smp.h
index e03a206..55ef31f 100644
--- a/include/asm-i386/smp.h
+++ b/include/asm-i386/smp.h
@@ -51,7 +51,7 @@
  * from the initial startup. We map APIC_BASE very early in page_setup(),
  * so this is correct in the x86 case.
  */
-#define __smp_processor_id() (current_thread_info()->cpu)
+#define raw_smp_processor_id() (current_thread_info()->cpu)
 
 extern cpumask_t cpu_callout_map;
 extern cpumask_t cpu_callin_map;
diff --git a/include/asm-i386/unistd.h b/include/asm-i386/unistd.h
index 61bcc1b..176413f 100644
--- a/include/asm-i386/unistd.h
+++ b/include/asm-i386/unistd.h
@@ -256,7 +256,7 @@
 #define __NR_io_submit		248
 #define __NR_io_cancel		249
 #define __NR_fadvise64		250
-
+#define __NR_set_zone_reclaim	251
 #define __NR_exit_group		252
 #define __NR_lookup_dcookie	253
 #define __NR_epoll_create	254
diff --git a/include/asm-ia64/mmzone.h b/include/asm-ia64/mmzone.h
index 9491dac..83ca404 100644
--- a/include/asm-ia64/mmzone.h
+++ b/include/asm-ia64/mmzone.h
@@ -15,6 +15,20 @@
 #include <asm/page.h>
 #include <asm/meminit.h>
 
+static inline int pfn_to_nid(unsigned long pfn)
+{
+#ifdef CONFIG_NUMA
+	extern int paddr_to_nid(unsigned long);
+	int nid = paddr_to_nid(pfn << PAGE_SHIFT);
+	if (nid < 0)
+		return 0;
+	else
+		return nid;
+#else
+	return 0;
+#endif
+}
+
 #ifdef CONFIG_DISCONTIGMEM
 
 #ifdef CONFIG_IA64_DIG /* DIG systems are small */
diff --git a/include/asm-ia64/pgtable.h b/include/asm-ia64/pgtable.h
index fcc9c33..48586e0 100644
--- a/include/asm-ia64/pgtable.h
+++ b/include/asm-ia64/pgtable.h
@@ -283,6 +283,7 @@
 #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
 #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
 #define pte_mkdirty(pte)	(__pte(pte_val(pte) | _PAGE_D))
+#define pte_mkhuge(pte)		(__pte(pte_val(pte) | _PAGE_P))
 
 /*
  * Macro to a page protection value as "uncacheable".  Note that "protection" is really a
diff --git a/include/asm-ia64/smp.h b/include/asm-ia64/smp.h
index 3ba1a06..a391435 100644
--- a/include/asm-ia64/smp.h
+++ b/include/asm-ia64/smp.h
@@ -46,7 +46,7 @@
 #define SMP_IRQ_REDIRECTION	(1 << 0)
 #define SMP_IPI_REDIRECTION	(1 << 1)
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id() (current_thread_info()->cpu)
 
 extern struct smp_boot_data {
 	int cpu_count;
diff --git a/include/asm-ia64/sn/mspec.h b/include/asm-ia64/sn/mspec.h
new file mode 100644
index 0000000..dbe13c6
--- /dev/null
+++ b/include/asm-ia64/sn/mspec.h
@@ -0,0 +1,59 @@
+/*
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * Copyright (c) 2001-2004 Silicon Graphics, Inc.  All rights reserved.
+ */
+
+#ifndef _ASM_IA64_SN_MSPEC_H
+#define _ASM_IA64_SN_MSPEC_H
+
+#define FETCHOP_VAR_SIZE 64 /* 64 byte per fetchop variable */
+
+#define FETCHOP_LOAD		0
+#define FETCHOP_INCREMENT	8
+#define FETCHOP_DECREMENT	16
+#define FETCHOP_CLEAR		24
+
+#define FETCHOP_STORE		0
+#define FETCHOP_AND		24
+#define FETCHOP_OR		32
+
+#define FETCHOP_CLEAR_CACHE	56
+
+#define FETCHOP_LOAD_OP(addr, op) ( \
+         *(volatile long *)((char*) (addr) + (op)))
+
+#define FETCHOP_STORE_OP(addr, op, x) ( \
+         *(volatile long *)((char*) (addr) + (op)) = (long) (x))
+
+#ifdef __KERNEL__
+
+/*
+ * Each Atomic Memory Operation (AMO formerly known as fetchop)
+ * variable is 64 bytes long.  The first 8 bytes are used.  The
+ * remaining 56 bytes are unaddressable due to the operation taking
+ * that portion of the address.
+ *
+ * NOTE: The AMO_t _MUST_ be placed in either the first or second half
+ * of the cache line.  The cache line _MUST NOT_ be used for anything
+ * other than additional AMO_t entries.  This is because there are two
+ * addresses which reference the same physical cache line.  One will
+ * be a cached entry with the memory type bits all set.  This address
+ * may be loaded into processor cache.  The AMO_t will be referenced
+ * uncached via the memory special memory type.  If any portion of the
+ * cached cache-line is modified, when that line is flushed, it will
+ * overwrite the uncached value in physical memory and lead to
+ * inconsistency.
+ */
+typedef struct {
+        u64 variable;
+        u64 unused[7];
+} AMO_t;
+
+
+#endif /* __KERNEL__ */
+
+#endif /* _ASM_IA64_SN_MSPEC_H */
diff --git a/include/asm-ia64/uncached.h b/include/asm-ia64/uncached.h
new file mode 100644
index 0000000..b82d923
--- /dev/null
+++ b/include/asm-ia64/uncached.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (C) 2001-2005 Silicon Graphics, Inc.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of version 2 of the GNU General Public License
+ * as published by the Free Software Foundation.
+ *
+ * Prototypes for the uncached page allocator
+ */
+
+extern unsigned long uncached_alloc_page(int nid);
+extern void uncached_free_page(unsigned long);
diff --git a/include/asm-ia64/unistd.h b/include/asm-ia64/unistd.h
index 33e26c5..f7f43ec 100644
--- a/include/asm-ia64/unistd.h
+++ b/include/asm-ia64/unistd.h
@@ -263,6 +263,7 @@
 #define __NR_add_key			1271
 #define __NR_request_key		1272
 #define __NR_keyctl			1273
+#define __NR_set_zone_reclaim		1276
 
 #ifdef __KERNEL__
 
diff --git a/include/asm-m32r/div64.h b/include/asm-m32r/div64.h
index 417a51b..6cd978c 100644
--- a/include/asm-m32r/div64.h
+++ b/include/asm-m32r/div64.h
@@ -1,38 +1 @@
-#ifndef _ASM_M32R_DIV64
-#define _ASM_M32R_DIV64
-
-/* $Id$ */
-
-/* unsigned long long division.
- * Input:
- *  unsigned long long  n
- *  unsigned long  base
- * Output:
- *  n = n / base;
- *  return value = n % base;
- */
-#define do_div(n, base)						\
-({								\
-	unsigned long _res, _high, _mid, _low;			\
-								\
-	_low = (n) & 0xffffffffUL;				\
-	_high = (n) >> 32;					\
-	if (_high) {						\
-		_mid = (_high % (unsigned long)(base)) << 16;	\
-		_high = _high / (unsigned long)(base);		\
-		_mid += _low >> 16;				\
-		_low &= 0x0000ffffUL;				\
-		_low += (_mid % (unsigned long)(base)) << 16;	\
-		_mid = _mid / (unsigned long)(base);		\
-		_res = _low % (unsigned long)(base);		\
-		_low = _low / (unsigned long)(base);		\
-		n = _low + ((long long)_mid << 16) +		\
-			((long long)_high << 32);		\
-	} else {						\
-		_res = _low % (unsigned long)(base);		\
-		n = (_low / (unsigned long)(base));		\
-	}							\
-	_res;							\
-})
-
-#endif  /* _ASM_M32R_DIV64 */
+#include <asm-generic/div64.h>
diff --git a/include/asm-m32r/ide.h b/include/asm-m32r/ide.h
index be64f24..194393b 100644
--- a/include/asm-m32r/ide.h
+++ b/include/asm-m32r/ide.h
@@ -35,7 +35,7 @@
 static __inline__ int ide_default_irq(unsigned long base)
 {
 	switch (base) {
-#if defined(CONFIG_PLAT_M32700UT) || defined(CONFIG_PLAT_MAPPI2)
+#if defined(CONFIG_PLAT_M32700UT) || defined(CONFIG_PLAT_MAPPI2) || defined(CONFIG_PLAT_MAPPI3)
 		case 0x1f0: return PLD_IRQ_CFIREQ;
 		default:
 			return 0;
diff --git a/include/asm-m32r/m32102.h b/include/asm-m32r/m32102.h
index b560340..cb98101 100644
--- a/include/asm-m32r/m32102.h
+++ b/include/asm-m32r/m32102.h
@@ -175,6 +175,7 @@
 #define M32R_ICU_CR5_PORTL    (0x210+M32R_ICU_OFFSET)  /* INT4 */
 #define M32R_ICU_CR6_PORTL    (0x214+M32R_ICU_OFFSET)  /* INT5 */
 #define M32R_ICU_CR7_PORTL    (0x218+M32R_ICU_OFFSET)  /* INT6 */
+#define M32R_ICU_CR8_PORTL    (0x219+M32R_ICU_OFFSET)  /* INT7 */
 #define M32R_ICU_CR16_PORTL   (0x23C+M32R_ICU_OFFSET)  /* MFT0 */
 #define M32R_ICU_CR17_PORTL   (0x240+M32R_ICU_OFFSET)  /* MFT1 */
 #define M32R_ICU_CR18_PORTL   (0x244+M32R_ICU_OFFSET)  /* MFT2 */
diff --git a/include/asm-m32r/m32102peri.h b/include/asm-m32r/m32102peri.h
deleted file mode 100644
index 3c12955..0000000
--- a/include/asm-m32r/m32102peri.h
+++ /dev/null
@@ -1,468 +0,0 @@
-/* $Id$
- *
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file "COPYING" in the main directory of this archive
- * for more details.
- *
- * Copyright (C) 2000,2001 by Hiroyuki Kondo
- */
-
-#ifndef __ASSEMBLY__
-
-typedef	void	V;
-typedef	char	B;
-typedef	short	S;
-typedef	int		W;
-typedef	long	L;
-typedef	float	F;
-typedef	double	D;
-typedef	unsigned char	UB;
-typedef	unsigned short	US;
-typedef	unsigned int	UW;
-typedef	unsigned long	UL;
-typedef	const unsigned int	CUW;
-
-/*********************************
-
-M32102 ICU
-
-*********************************/
-#define		ICUISTS		(UW *)0xa0EFF004
-#define		ICUIREQ0	(UW *)0xa0EFF008
-#define		ICUIREQ1	(UW *)0xa0EFF00C
-
-#define		ICUSBICR	(UW *)0xa0EFF018
-#define		ICUIMASK	(UW *)0xa0EFF01C
-
-#define		ICUCR1		(UW *)0xa0EFF200	/* INT0 */
-#define		ICUCR2		(UW *)0xa0EFF204	/* INT1 */
-#define		ICUCR3		(UW *)0xa0EFF208	/* INT2 */
-#define		ICUCR4		(UW *)0xa0EFF20C	/* INT3 */
-#define		ICUCR5		(UW *)0xa0EFF210	/* INT4 */
-#define		ICUCR6		(UW *)0xa0EFF214	/* INT5 */
-#define		ICUCR7		(UW *)0xa0EFF218	/* INT6 */
-
-#define		ICUCR16		(UW *)0xa0EFF23C	/* MFT0 */
-#define		ICUCR17		(UW *)0xa0EFF240	/* MFT1 */
-#define		ICUCR18		(UW *)0xa0EFF244	/* MFT2 */
-#define		ICUCR19		(UW *)0xa0EFF248	/* MFT3 */
-#define		ICUCR20		(UW *)0xa0EFF24C	/* MFT4 */
-#define		ICUCR21		(UW *)0xa0EFF250	/* MFT5 */
-
-#define		ICUCR32		(UW *)0xa0EFF27C	/* DMA0 */
-#define		ICUCR33		(UW *)0xa0EFF280	/* DMA1 */
-
-#define		ICUCR48		(UW *)0xa0EFF2BC	/* SIO0R */
-#define		ICUCR49		(UW *)0xa0EFF2C0	/* SIO0S */
-#define		ICUCR50		(UW *)0xa0EFF2C4	/* SIO1R */
-#define		ICUCR51		(UW *)0xa0EFF2C8	/* SIO1S */
-#define		ICUCR52		(UW *)0xa0EFF2CC	/* SIO2R */
-#define		ICUCR53		(UW *)0xa0EFF2D0	/* SIO2S */
-#define		ICUCR54		(UW *)0xa0EFF2D4	/* SIO3R */
-#define		ICUCR55		(UW *)0xa0EFF2D8	/* SIO3S */
-#define		ICUCR56		(UW *)0xa0EFF2DC	/* SIO4R */
-#define		ICUCR57		(UW *)0xa0EFF2E0	/* SIO4S */
-
-/*********************************
-
-M32102 MFT
-
-*********************************/
-#define		MFTCR		(US *)0xa0EFC002
-#define		MFTRPR		(UB *)0xa0EFC006
-
-#define		MFT0MOD		(US *)0xa0EFC102
-#define		MFT0BOS		(US *)0xa0EFC106
-#define		MFT0CUT		(US *)0xa0EFC10A
-#define		MFT0RLD		(US *)0xa0EFC10E
-#define		MFT0CRLD	(US *)0xa0EFC112
-
-#define		MFT1MOD		(US *)0xa0EFC202
-#define		MFT1BOS		(US *)0xa0EFC206
-#define		MFT1CUT		(US *)0xa0EFC20A
-#define		MFT1RLD		(US *)0xa0EFC20E
-#define		MFT1CRLD	(US *)0xa0EFC212
-
-#define		MFT2MOD		(US *)0xa0EFC302
-#define		MFT2BOS		(US *)0xa0EFC306
-#define		MFT2CUT		(US *)0xa0EFC30A
-#define		MFT2RLD		(US *)0xa0EFC30E
-#define		MFT2CRLD	(US *)0xa0EFC312
-
-#define		MFT3MOD		(US *)0xa0EFC402
-#define		MFT3CUT		(US *)0xa0EFC40A
-#define		MFT3RLD		(US *)0xa0EFC40E
-#define		MFT3CRLD	(US *)0xa0EFC412
-
-#define		MFT4MOD		(US *)0xa0EFC502
-#define		MFT4CUT		(US *)0xa0EFC50A
-#define		MFT4RLD		(US *)0xa0EFC50E
-#define		MFT4CRLD	(US *)0xa0EFC512
-
-#define		MFT5MOD		(US *)0xa0EFC602
-#define		MFT5CUT		(US *)0xa0EFC60A
-#define		MFT5RLD		(US *)0xa0EFC60E
-#define		MFT5CRLD	(US *)0xa0EFC612
-
-/*********************************
-
-M32102 SIO
-
-*********************************/
-
-#define SIO0CR     (volatile int *)0xa0efd000
-#define SIO0MOD0   (volatile int *)0xa0efd004
-#define SIO0MOD1   (volatile int *)0xa0efd008
-#define SIO0STS    (volatile int *)0xa0efd00c
-#define SIO0IMASK  (volatile int *)0xa0efd010
-#define SIO0BAUR   (volatile int *)0xa0efd014
-#define SIO0RBAUR  (volatile int *)0xa0efd018
-#define SIO0TXB    (volatile int *)0xa0efd01c
-#define SIO0RXB    (volatile int *)0xa0efd020
-
-#define SIO1CR     (volatile int *)0xa0efd100
-#define SIO1MOD0   (volatile int *)0xa0efd104
-#define SIO1MOD1   (volatile int *)0xa0efd108
-#define SIO1STS    (volatile int *)0xa0efd10c
-#define SIO1IMASK  (volatile int *)0xa0efd110
-#define SIO1BAUR   (volatile int *)0xa0efd114
-#define SIO1RBAUR  (volatile int *)0xa0efd118
-#define SIO1TXB    (volatile int *)0xa0efd11c
-#define SIO1RXB    (volatile int *)0xa0efd120
-/*********************************
-
-M32102 PORT
-
-*********************************/
-#define		PIEN		(UB *)0xa0EF1003	/* input enable */
-
-#define		P0DATA		(UB *)0xa0EF1020	/* data */
-#define		P1DATA		(UB *)0xa0EF1021
-#define		P2DATA		(UB *)0xa0EF1022
-#define		P3DATA		(UB *)0xa0EF1023
-#define		P4DATA		(UB *)0xa0EF1024
-#define		P5DATA		(UB *)0xa0EF1025
-#define		P6DATA		(UB *)0xa0EF1026
-#define		P7DATA		(UB *)0xa0EF1027
-
-#define		P0DIR		(UB *)0xa0EF1040	/* direction */
-#define		P1DIR		(UB *)0xa0EF1041
-#define		P2DIR		(UB *)0xa0EF1042
-#define		P3DIR		(UB *)0xa0EF1043
-#define		P4DIR		(UB *)0xa0EF1044
-#define		P5DIR		(UB *)0xa0EF1045
-#define		P6DIR		(UB *)0xa0EF1046
-#define		P7DIR		(UB *)0xa0EF1047
-
-#define		P0MOD		(US *)0xa0EF1060	/* mode control */
-#define		P1MOD		(US *)0xa0EF1062
-#define		P2MOD		(US *)0xa0EF1064
-#define		P3MOD		(US *)0xa0EF1066
-#define		P4MOD		(US *)0xa0EF1068
-#define		P5MOD		(US *)0xa0EF106A
-#define		P6MOD		(US *)0xa0EF106C
-#define		P7MOD		(US *)0xa0EF106E
-
-#define		P0ODCR		(UB *)0xa0EF1080	/* open-drain control */
-#define		P1ODCR		(UB *)0xa0EF1081
-#define		P2ODCR		(UB *)0xa0EF1082
-#define		P3ODCR		(UB *)0xa0EF1083
-#define		P4ODCR		(UB *)0xa0EF1084
-#define		P5ODCR		(UB *)0xa0EF1085
-#define		P6ODCR		(UB *)0xa0EF1086
-#define		P7ODCR		(UB *)0xa0EF1087
-
-/*********************************
-
-M32102 Cache
-
-********************************/
-
-#define		MCCR	(US *)0xFFFFFFFE
-
-
-#else  /* __ASSEMBLY__ */
-
-;;
-;; PIO     0x80ef1000
-;;
-
-#define PIEN          0xa0ef1000
-
-#define P0DATA        0xa0ef1020
-#define P1DATA        0xa0ef1021
-#define P2DATA        0xa0ef1022
-#define P3DATA        0xa0ef1023
-#define P4DATA        0xa0ef1024
-#define P5DATA        0xa0ef1025
-#define P6DATA        0xa0ef1026
-#define P7DATA        0xa0ef1027
-
-#define P0DIR         0xa0ef1040
-#define P1DIR         0xa0ef1041
-#define P2DIR         0xa0ef1042
-#define P3DIR         0xa0ef1043
-#define P4DIR         0xa0ef1044
-#define P5DIR         0xa0ef1045
-#define P6DIR         0xa0ef1046
-#define P7DIR         0xa0ef1047
-
-#define P0MOD         0xa0ef1060
-#define P1MOD         0xa0ef1062
-#define P2MOD         0xa0ef1064
-#define P3MOD         0xa0ef1066
-#define P4MOD         0xa0ef1068
-#define P5MOD         0xa0ef106a
-#define P6MOD         0xa0ef106c
-#define P7MOD         0xa0ef106e
-;
-#define P0ODCR        0xa0ef1080
-#define P1ODCR        0xa0ef1081
-#define P2ODCR        0xa0ef1082
-#define P3ODCR        0xa0ef1083
-#define P4ODCR        0xa0ef1084
-#define P5ODCR        0xa0ef1085
-#define P6ODCR        0xa0ef1086
-#define P7ODCR        0xa0ef1087
-
-;;
-;; WDT     0xa0ef2000
-;;
-
-#define WDTCR         0xa0ef2000
-
-
-;;
-;; CLK     0xa0ef4000
-;;
-
-#define CPUCLKCR      0xa0ef4000
-#define CLKMOD        0xa0ef4004
-#define PLLCR         0xa0ef4008
-
-
-;;
-;; BSEL    0xa0ef5000
-;;
-
-#define BSEL0CR       0xa0ef5000
-#define BSEL1CR       0xa0ef5004
-#define BSEL2CR       0xa0ef5008
-#define BSEL3CR       0xa0ef500c
-#define BSEL4CR       0xa0ef5010
-#define BSEL5CR       0xa0ef5014
-
-
-;;
-;; SDRAMC  0xa0ef6000
-;;
-
-#define SDRF0         0xa0ef6000
-#define SDRF1         0xa0ef6004
-#define SDIR0         0xa0ef6008
-#define SDIR1         0xa0ef600c
-#define SDBR          0xa0ef6010
-
-;; CH0
-#define SD0ADR        0xa0ef6020
-#define SD0SZ         0xa0ef6022
-#define SD0ER         0xa0ef6024
-#define SD0TR         0xa0ef6028
-#define SD0MOD        0xa0ef602c
-
-;; CH1
-#define SD1ADR        0xa0ef6040
-#define SD1SZ         0xa0ef6042
-#define SD1ER         0xa0ef6044
-#define SD1TR         0xa0ef6048
-#define SD1MOD        0xa0ef604c
-
-
-;;
-;; DMAC    0xa0ef8000
-;;
-
-#define DMAEN         0xa0ef8000
-#define DMAISTS       0xa0ef8004
-#define DMAEDET       0xa0ef8008
-#define DMAASTS       0xa0ef800c
-
-;; CH0
-#define DMA0CR0       0xa0ef8100
-#define DMA0CR1       0xa0ef8104
-#define DMA0CSA       0xa0ef8108
-#define DMA0RSA       0xa0ef810c
-#define DMA0CDA       0xa0ef8110
-#define DMA0RDA       0xa0ef8114
-#define DMA0CBCUT     0xa0ef8118
-#define DMA0RBCUT     0xa0ef811c
-
-;; CH1
-#define DMA1CR0       0xa0ef8200
-#define DMA1CR1       0xa0ef8204
-#define DMA1CSA       0xa0ef8208
-#define DMA1RSA       0xa0ef820c
-#define DMA1CDA       0xa0ef8210
-#define DMA1RDA       0xa0ef8214
-#define DMA1CBCUT     0xa0ef8218
-#define DMA1RBCUT     0xa0ef821c
-
-
-;;
-;; MFT     0xa0efc000
-;;
-
-#define MFTCR        0xa0efc000
-#define MFTRPR       0xa0efc004
-
-;; CH0
-#define MFT0MOD      0xa0efc100
-#define MFT0BOS      0xa0efc104
-#define MFT0CUT      0xa0efc108
-#define MFT0RLD      0xa0efc10c
-#define MFT0CMPRLD   0xa0efc110
-
-;; CH1
-#define MFT1MOD      0xa0efc200
-#define MFT1BOS      0xa0efc204
-#define MFT1CUT      0xa0efc208
-#define MFT1RLD      0xa0efc20c
-#define MFT1CMPRLD   0xa0efc210
-
-;; CH2
-#define MFT2MOD      0xa0efc300
-#define MFT2BOS      0xa0efc304
-#define MFT2CUT      0xa0efc308
-#define MFT2RLD      0xa0efc30c
-#define MFT2CMPRLD   0xa0efc310
-
-;; CH3
-#define MFT3MOD      0xa0efc400
-#define MFT3BOS      0xa0efc404
-#define MFT3CUT      0xa0efc408
-#define MFT3RLD      0xa0efc40c
-#define MFT3CMPRLD   0xa0efc410
-
-;; CH4
-#define MFT4MOD      0xa0efc500
-#define MFT4BOS      0xa0efc504
-#define MFT4CUT      0xa0efc508
-#define MFT4RLD      0xa0efc50c
-#define MFT4CMPRLD   0xa0efc510
-
-;; CH5
-#define MFT5MOD      0xa0efc600
-#define MFT5BOS      0xa0efc604
-#define MFT5CUT      0xa0efc608
-#define MFT5RLD      0xa0efc60c
-#define MFT5CMPRLD   0xa0efc610
-
-
-;;
-;; SIO     0xa0efd000
-;;
-
-;; CH0
-#define SIO0CR        0xa0efd000
-#define SIO0MOD0      0xa0efd004
-#define SIO0MOD1      0xa0efd008
-#define SIO0STS       0xa0efd00c
-#define SIO0IMASK     0xa0efd010
-#define SIO0BAUR      0xa0efd014
-#define SIO0RBAUR     0xa0efd018
-#define SIO0TXB       0xa0efd01c
-#define SIO0RXB       0xa0efd020
-
-;; CH1
-#define SIO1CR        0xa0efd100
-#define SIO1MOD0      0xa0efd104
-#define SIO1MOD1      0xa0efd108
-#define SIO1STS       0xa0efd10c
-#define SIO1IMASK     0xa0efd110
-#define SIO1BAUR      0xa0efd114
-#define SIO1RBAUR     0xa0efd118
-#define SIO1TXB       0xa0efd11c
-#define SIO1RXB       0xa0efd120
-
-;; CH2
-#define SIO2CR        0xa0efd200
-#define SIO2MOD0      0xa0efd204
-#define SIO2MOD1      0xa0efd208
-#define SIO2STS       0xa0efd20c
-#define SIO2IMASK     0xa0efd210
-#define SIO2BAUR      0xa0efd214
-#define SIO2RBAUR     0xa0efd218
-#define SIO2TXB       0xa0efd21c
-#define SIO2RXB       0xa0efd220
-
-;; CH3
-#define SIO3CR        0xa0efd300
-#define SIO3MOD0      0xa0efd304
-#define SIO3MOD1      0xa0efd308
-#define SIO3STS       0xa0efd30c
-#define SIO3IMASK     0xa0efd310
-#define SIO3BAUR      0xa0efd314
-#define SIO3RBAUR     0xa0efd318
-#define SIO3TXB       0xa0efd31c
-#define SIO3RXB       0xa0efd320
-
-;; CH4
-#define SIO4CR        0xa0efd400
-#define SIO4MOD0      0xa0efd404
-#define SIO4MOD1      0xa0efd408
-#define SIO4STS       0xa0efd40c
-#define SIO4IMASK     0xa0efd410
-#define SIO4BAUR      0xa0efd414
-#define SIO4RBAUR     0xa0efd418
-#define SIO4TXB       0xa0efd41c
-#define SIO4RXB       0xa0efd420
-
-
-;;
-;; ICU     0xa0eff000
-;;
-
-#define ICUISTS       0xa0eff004
-#define ICUIREQ0      0xa0eff008
-#define ICUIREQ1      0xa0eff00c
-
-#define ICUSBICR      0xa0eff018
-#define ICUIMASK      0xa0eff01c
-
-#define ICUCR1        0xa0eff200
-#define ICUCR2        0xa0eff204
-#define ICUCR3        0xa0eff208
-#define ICUCR4        0xa0eff20c
-#define ICUCR5        0xa0eff210
-#define ICUCR6        0xa0eff214
-#define ICUCR7        0xa0eff218
-
-#define ICUCR16       0xa0eff23c
-#define ICUCR17       0xa0eff240
-#define ICUCR18       0xa0eff244
-#define ICUCR19       0xa0eff248
-#define ICUCR20       0xa0eff24c
-#define ICUCR21       0xa0eff250
-
-#define ICUCR32       0xa0eff27c
-#define ICUCR33       0xa0eff280
-
-#define ICUCR48       0xa0eff2bc
-#define ICUCR49       0xa0eff2c0
-#define ICUCR50       0xa0eff2c4
-#define ICUCR51       0xa0eff2c8
-#define ICUCR52       0xa0eff2cc
-#define ICUCR53       0xa0eff2d0
-#define ICUCR54       0xa0eff2d4
-#define ICUCR55       0xa0eff2d8
-#define ICUCR56       0xa0eff2dc
-#define ICUCR57       0xa0eff2e0
-
-;;
-;; CACHE
-;;
-
-#define MCCR		  0xfffffffc
-
-
-#endif  /* __ASSEMBLY__ */
diff --git a/include/asm-m32r/m32r.h b/include/asm-m32r/m32r.h
index f116649..ec142be 100644
--- a/include/asm-m32r/m32r.h
+++ b/include/asm-m32r/m32r.h
@@ -16,7 +16,6 @@
 	|| defined(CONFIG_CHIP_M32700) || defined(CONFIG_CHIP_M32102) \
         || defined(CONFIG_CHIP_OPSP)
 #include <asm/m32102.h>
-#include <asm/m32102peri.h>
 #endif
 
 /* Platform type */
@@ -36,6 +35,10 @@
 #include <asm/mappi2/mappi2_pld.h>
 #endif	/* CONFIG_PLAT_MAPPI2 */
 
+#if defined(CONFIG_PLAT_MAPPI3)
+#include <asm/mappi3/mappi3_pld.h>
+#endif	/* CONFIG_PLAT_MAPPI3 */
+
 #if defined(CONFIG_PLAT_USRV)
 #include <asm/m32700ut/m32700ut_pld.h>
 #endif
diff --git a/include/asm-m32r/mappi3/mappi3_pld.h b/include/asm-m32r/mappi3/mappi3_pld.h
new file mode 100644
index 0000000..3f1551f
--- /dev/null
+++ b/include/asm-m32r/mappi3/mappi3_pld.h
@@ -0,0 +1,143 @@
+/*
+ * include/asm/mappi3/mappi3_pld.h
+ *
+ * Definitions for Extended IO Logic on MAPPI3 board.
+ *  based on m32700ut_pld.h
+ *
+ * This file is subject to the terms and conditions of the GNU General
+ * Public License.  See the file "COPYING" in the main directory of
+ * this archive for more details.
+ *
+ */
+
+#ifndef _MAPPI3_PLD_H
+#define _MAPPI3_PLD_H
+
+#ifndef __ASSEMBLY__
+/* FIXME:
+ * Some C functions use non-cache address, so can't define non-cache address.
+ */
+#define PLD_BASE		(0x1c000000 /* + NONCACHE_OFFSET */)
+#define __reg8			(volatile unsigned char *)
+#define __reg16			(volatile unsigned short *)
+#define __reg32			(volatile unsigned int *)
+#else
+#define PLD_BASE		(0x1c000000 + NONCACHE_OFFSET)
+#define __reg8
+#define __reg16
+#define __reg32
+#endif	/* __ASSEMBLY__ */
+
+/* CFC */
+#define	PLD_CFRSTCR		__reg16(PLD_BASE + 0x0000)
+#define PLD_CFSTS		__reg16(PLD_BASE + 0x0002)
+#define PLD_CFIMASK		__reg16(PLD_BASE + 0x0004)
+#define PLD_CFBUFCR		__reg16(PLD_BASE + 0x0006)
+#define PLD_CFCR0		__reg16(PLD_BASE + 0x000a)
+#define PLD_CFCR1		__reg16(PLD_BASE + 0x000c)
+
+/* MMC */
+#define PLD_MMCCR		__reg16(PLD_BASE + 0x4000)
+#define PLD_MMCMOD		__reg16(PLD_BASE + 0x4002)
+#define PLD_MMCSTS		__reg16(PLD_BASE + 0x4006)
+#define PLD_MMCBAUR		__reg16(PLD_BASE + 0x400a)
+#define PLD_MMCCMDBCUT		__reg16(PLD_BASE + 0x400c)
+#define PLD_MMCCDTBCUT		__reg16(PLD_BASE + 0x400e)
+#define PLD_MMCDET		__reg16(PLD_BASE + 0x4010)
+#define PLD_MMCWP		__reg16(PLD_BASE + 0x4012)
+#define PLD_MMCWDATA		__reg16(PLD_BASE + 0x5000)
+#define PLD_MMCRDATA		__reg16(PLD_BASE + 0x6000)
+#define PLD_MMCCMDDATA		__reg16(PLD_BASE + 0x7000)
+#define PLD_MMCRSPDATA		__reg16(PLD_BASE + 0x7006)
+
+/* Power Control of MMC and CF */
+#define PLD_CPCR		__reg16(PLD_BASE + 0x14000)
+
+
+/*==== ICU ====*/
+#define  M32R_IRQ_PC104        (5)   /* INT4(PC/104) */
+#define  M32R_IRQ_I2C          (28)  /* I2C-BUS     */
+#define  PLD_IRQ_CFIREQ       (6)  /* INT5 CFC Card Interrupt */
+#define  PLD_IRQ_CFC_INSERT   (7)  /* INT6 CFC Card Insert */
+#define  PLD_IRQ_CFC_EJECT    (8)  /* INT7 CFC Card Eject */
+#define  PLD_IRQ_MMCCARD      (43)  /* MMC Card Insert */
+#define  PLD_IRQ_MMCIRQ       (44)  /* MMC Transfer Done */
+
+
+#if 0
+/* LED Control
+ *
+ * 1: DIP swich side
+ * 2: Reset switch side
+ */
+#define PLD_IOLEDCR		__reg16(PLD_BASE + 0x14002)
+#define PLD_IOLED_1_ON		0x001
+#define PLD_IOLED_1_OFF		0x000
+#define PLD_IOLED_2_ON		0x002
+#define PLD_IOLED_2_OFF		0x000
+
+/* DIP Switch
+ *  0: Write-protect of Flash Memory (0:protected, 1:non-protected)
+ *  1: -
+ *  2: -
+ *  3: -
+ */
+#define PLD_IOSWSTS		__reg16(PLD_BASE + 0x14004)
+#define	PLD_IOSWSTS_IOSW2	0x0200
+#define	PLD_IOSWSTS_IOSW1	0x0100
+#define	PLD_IOSWSTS_IOWP0	0x0001
+
+#endif
+
+/* CRC */
+#define PLD_CRC7DATA		__reg16(PLD_BASE + 0x18000)
+#define PLD_CRC7INDATA		__reg16(PLD_BASE + 0x18002)
+#define PLD_CRC16DATA		__reg16(PLD_BASE + 0x18004)
+#define PLD_CRC16INDATA		__reg16(PLD_BASE + 0x18006)
+#define PLD_CRC16ADATA		__reg16(PLD_BASE + 0x18008)
+#define PLD_CRC16AINDATA	__reg16(PLD_BASE + 0x1800a)
+
+
+#if 0
+/* RTC */
+#define PLD_RTCCR		__reg16(PLD_BASE + 0x1c000)
+#define PLD_RTCBAUR		__reg16(PLD_BASE + 0x1c002)
+#define PLD_RTCWRDATA		__reg16(PLD_BASE + 0x1c004)
+#define PLD_RTCRDDATA		__reg16(PLD_BASE + 0x1c006)
+#define PLD_RTCRSTODT		__reg16(PLD_BASE + 0x1c008)
+
+/* SIO0 */
+#define PLD_ESIO0CR		__reg16(PLD_BASE + 0x20000)
+#define	PLD_ESIO0CR_TXEN	0x0001
+#define	PLD_ESIO0CR_RXEN	0x0002
+#define PLD_ESIO0MOD0		__reg16(PLD_BASE + 0x20002)
+#define	PLD_ESIO0MOD0_CTSS	0x0040
+#define	PLD_ESIO0MOD0_RTSS	0x0080
+#define PLD_ESIO0MOD1		__reg16(PLD_BASE + 0x20004)
+#define	PLD_ESIO0MOD1_LMFS	0x0010
+#define PLD_ESIO0STS		__reg16(PLD_BASE + 0x20006)
+#define	PLD_ESIO0STS_TEMP	0x0001
+#define	PLD_ESIO0STS_TXCP	0x0002
+#define	PLD_ESIO0STS_RXCP	0x0004
+#define	PLD_ESIO0STS_TXSC	0x0100
+#define	PLD_ESIO0STS_RXSC	0x0200
+#define PLD_ESIO0STS_TXREADY	(PLD_ESIO0STS_TXCP | PLD_ESIO0STS_TEMP)
+#define PLD_ESIO0INTCR		__reg16(PLD_BASE + 0x20008)
+#define	PLD_ESIO0INTCR_TXIEN	0x0002
+#define	PLD_ESIO0INTCR_RXCEN	0x0004
+#define PLD_ESIO0BAUR		__reg16(PLD_BASE + 0x2000a)
+#define PLD_ESIO0TXB		__reg16(PLD_BASE + 0x2000c)
+#define PLD_ESIO0RXB		__reg16(PLD_BASE + 0x2000e)
+
+/* SIM Card */
+#define PLD_SCCR		__reg16(PLD_BASE + 0x38000)
+#define PLD_SCMOD		__reg16(PLD_BASE + 0x38004)
+#define PLD_SCSTS		__reg16(PLD_BASE + 0x38006)
+#define PLD_SCINTCR		__reg16(PLD_BASE + 0x38008)
+#define PLD_SCBAUR		__reg16(PLD_BASE + 0x3800a)
+#define PLD_SCTXB		__reg16(PLD_BASE + 0x3800c)
+#define PLD_SCRXB		__reg16(PLD_BASE + 0x3800e)
+
+#endif
+
+#endif	/* _MAPPI3_PLD.H */
diff --git a/include/asm-m32r/smp.h b/include/asm-m32r/smp.h
index 8cd4d0d..b9a20cd 100644
--- a/include/asm-m32r/smp.h
+++ b/include/asm-m32r/smp.h
@@ -66,7 +66,7 @@
 #define physid_to_cpu(physid)	physid_2_cpu[physid]
 #define cpu_to_physid(cpu_id)	cpu_2_physid[cpu_id]
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id()	(current_thread_info()->cpu)
 
 extern cpumask_t cpu_callout_map;
 #define cpu_possible_map cpu_callout_map
diff --git a/include/asm-mips/smp.h b/include/asm-mips/smp.h
index 8ba370e..5618f1e 100644
--- a/include/asm-mips/smp.h
+++ b/include/asm-mips/smp.h
@@ -21,7 +21,7 @@
 #include <linux/cpumask.h>
 #include <asm/atomic.h>
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id() (current_thread_info()->cpu)
 
 /* Map from cpu id to sequential logical cpu number.  This will only
    not be idempotent when cpus failed to come on-line.  */
diff --git a/include/asm-mips/vr41xx/giu.h b/include/asm-mips/vr41xx/giu.h
new file mode 100644
index 0000000..8590885
--- /dev/null
+++ b/include/asm-mips/vr41xx/giu.h
@@ -0,0 +1,69 @@
+/*
+ *  Include file for NEC VR4100 series General-purpose I/O Unit.
+ *
+ *  Copyright (C) 2005  Yoichi Yuasa <yuasa@hh.iij4u.or.jp>
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+#ifndef __NEC_VR41XX_GIU_H
+#define __NEC_VR41XX_GIU_H
+
+typedef enum {
+	IRQ_TRIGGER_LEVEL,
+	IRQ_TRIGGER_EDGE,
+	IRQ_TRIGGER_EDGE_FALLING,
+	IRQ_TRIGGER_EDGE_RISING,
+} irq_trigger_t;
+
+typedef enum {
+	IRQ_SIGNAL_THROUGH,
+	IRQ_SIGNAL_HOLD,
+} irq_signal_t;
+
+extern void vr41xx_set_irq_trigger(unsigned int pin, irq_trigger_t trigger, irq_signal_t signal);
+
+typedef enum {
+	IRQ_LEVEL_LOW,
+	IRQ_LEVEL_HIGH,
+} irq_level_t;
+
+extern void vr41xx_set_irq_level(unsigned int pin, irq_level_t level);
+
+typedef enum {
+	GPIO_DATA_LOW,
+	GPIO_DATA_HIGH,
+	GPIO_DATA_INVAL,
+} gpio_data_t;
+
+extern gpio_data_t vr41xx_gpio_get_pin(unsigned int pin);
+extern int vr41xx_gpio_set_pin(unsigned int pin, gpio_data_t data);
+
+typedef enum {
+	GPIO_INPUT,
+	GPIO_OUTPUT,
+	GPIO_OUTPUT_DISABLE,
+} gpio_direction_t;
+
+extern int vr41xx_gpio_set_direction(unsigned int pin, gpio_direction_t dir);
+
+typedef enum {
+	GPIO_PULL_DOWN,
+	GPIO_PULL_UP,
+	GPIO_PULL_DISABLE,
+} gpio_pull_t;
+
+extern int vr41xx_gpio_pullupdown(unsigned int pin, gpio_pull_t pull);
+
+#endif /* __NEC_VR41XX_GIU_H */
diff --git a/include/asm-mips/vr41xx/vr41xx.h b/include/asm-mips/vr41xx/vr41xx.h
index ad0d1ea..7d41e44 100644
--- a/include/asm-mips/vr41xx/vr41xx.h
+++ b/include/asm-mips/vr41xx/vr41xx.h
@@ -126,7 +126,6 @@
 #define GIU_IRQ_BASE		40
 #define GIU_IRQ(x)		(GIU_IRQ_BASE + (x))	/* IRQ 40-71 */
 #define GIU_IRQ_LAST		GIU_IRQ(31)
-#define GIU_IRQ_TO_PIN(x)	((x) - GIU_IRQ_BASE)	/* Pin 0-31 */
 
 extern int vr41xx_set_intassign(unsigned int irq, unsigned char intassign);
 extern int vr41xx_cascade_irq(unsigned int irq, int (*get_irq_number)(int irq));
@@ -197,38 +196,4 @@
 extern void vr41xx_enable_bcuint(void);
 extern void vr41xx_disable_bcuint(void);
 
-/*
- * General-Purpose I/O Unit
- */
-enum {
-	TRIGGER_LEVEL,
-	TRIGGER_EDGE,
-	TRIGGER_EDGE_FALLING,
-	TRIGGER_EDGE_RISING
-};
-
-enum {
-	SIGNAL_THROUGH,
-	SIGNAL_HOLD
-};
-
-extern void vr41xx_set_irq_trigger(int pin, int trigger, int hold);
-
-enum {
-	LEVEL_LOW,
-	LEVEL_HIGH
-};
-
-extern void vr41xx_set_irq_level(int pin, int level);
-
-enum {
-	PIO_INPUT,
-	PIO_OUTPUT
-};
-
-enum {
-	DATA_LOW,
-	DATA_HIGH
-};
-
 #endif /* __NEC_VR41XX_H */
diff --git a/include/asm-parisc/smp.h b/include/asm-parisc/smp.h
index fde77ac..9413f67 100644
--- a/include/asm-parisc/smp.h
+++ b/include/asm-parisc/smp.h
@@ -51,7 +51,7 @@
 
 extern unsigned long cpu_present_mask;
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id()	(current_thread_info()->cpu)
 
 #endif /* CONFIG_SMP */
 
diff --git a/include/asm-ppc/irq.h b/include/asm-ppc/irq.h
index 06b86be..a9b3332 100644
--- a/include/asm-ppc/irq.h
+++ b/include/asm-ppc/irq.h
@@ -176,7 +176,7 @@
 */
 #include <asm/mpc85xx.h>
 
-/* The MPC8560 openpic has  32 internal interrupts and 12 external
+/* The MPC8548 openpic has 48 internal interrupts and 12 external
  * interrupts.
  *
  * We are "flattening" the interrupt vectors of the cascaded CPM
@@ -184,7 +184,7 @@
  * single integer.
  */
 #define NR_CPM_INTS	64
-#define NR_EPIC_INTS	44
+#define NR_EPIC_INTS	60
 #ifndef NR_8259_INTS
 #define NR_8259_INTS	0
 #endif
@@ -223,9 +223,15 @@
 #define MPC85xx_IRQ_RIO_RX	(12 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_TSEC1_TX	(13 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_TSEC1_RX	(14 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_TSEC3_TX	(15 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_TSEC3_RX	(16 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_TSEC3_ERROR	(17 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_TSEC1_ERROR	(18 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_TSEC2_TX	(19 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_TSEC2_RX	(20 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_TSEC4_TX	(21 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_TSEC4_RX	(22 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_TSEC4_ERROR	(23 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_TSEC2_ERROR	(24 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_FEC		(25 + MPC85xx_OPENPIC_IRQ_OFFSET)
 #define MPC85xx_IRQ_DUART	(26 + MPC85xx_OPENPIC_IRQ_OFFSET)
@@ -235,18 +241,18 @@
 #define MPC85xx_IRQ_CPM		(30 + MPC85xx_OPENPIC_IRQ_OFFSET)
 
 /* The 12 external interrupt lines */
-#define MPC85xx_IRQ_EXT0        (32 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT1        (33 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT2        (34 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT3        (35 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT4        (36 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT5        (37 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT6        (38 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT7        (39 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT8        (40 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT9        (41 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT10       (42 + MPC85xx_OPENPIC_IRQ_OFFSET)
-#define MPC85xx_IRQ_EXT11       (43 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT0        (48 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT1        (49 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT2        (50 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT3        (51 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT4        (52 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT5        (53 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT6        (54 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT7        (55 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT8        (56 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT9        (57 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT10       (58 + MPC85xx_OPENPIC_IRQ_OFFSET)
+#define MPC85xx_IRQ_EXT11       (59 + MPC85xx_OPENPIC_IRQ_OFFSET)
 
 /* CPM related interrupts */
 #define	SIU_INT_ERROR		((uint)0x00+CPM_IRQ_OFFSET)
diff --git a/include/asm-ppc/mpc10x.h b/include/asm-ppc/mpc10x.h
index d8e7e2d..f5196a4 100644
--- a/include/asm-ppc/mpc10x.h
+++ b/include/asm-ppc/mpc10x.h
@@ -159,6 +159,12 @@
 #define	MPC10X_MAPA_EUMB_BASE		(ioremap_base - MPC10X_EUMB_SIZE)
 #define	MPC10X_MAPB_EUMB_BASE		MPC10X_MAPA_EUMB_BASE
 
+enum ppc_sys_devices {
+	MPC10X_IIC1,
+	MPC10X_DMA0,
+	MPC10X_DMA1,
+	MPC10X_DUART,
+};
 
 int mpc10x_bridge_init(struct pci_controller *hose,
 		       uint current_map,
diff --git a/include/asm-ppc/mpc85xx.h b/include/asm-ppc/mpc85xx.h
index 22713e3..516984e 100644
--- a/include/asm-ppc/mpc85xx.h
+++ b/include/asm-ppc/mpc85xx.h
@@ -25,7 +25,7 @@
 #ifdef CONFIG_MPC8540_ADS
 #include <platforms/85xx/mpc8540_ads.h>
 #endif
-#ifdef CONFIG_MPC8555_CDS
+#if defined(CONFIG_MPC8555_CDS) || defined(CONFIG_MPC8548_CDS)
 #include <platforms/85xx/mpc8555_cds.h>
 #endif
 #ifdef CONFIG_MPC8560_ADS
@@ -74,7 +74,7 @@
 #define MPC85xx_GUTS_OFFSET	(0xe0000)
 #define MPC85xx_GUTS_SIZE	(0x01000)
 #define MPC85xx_IIC1_OFFSET	(0x03000)
-#define MPC85xx_IIC1_SIZE	(0x01000)
+#define MPC85xx_IIC1_SIZE	(0x00100)
 #define MPC85xx_OPENPIC_OFFSET	(0x40000)
 #define MPC85xx_OPENPIC_SIZE	(0x40000)
 #define MPC85xx_PCI1_OFFSET	(0x08000)
@@ -127,8 +127,64 @@
 	MPC85xx_CPM_MCC2,
 	MPC85xx_CPM_SMC1,
 	MPC85xx_CPM_SMC2,
+	MPC85xx_eTSEC1,
+	MPC85xx_eTSEC2,
+	MPC85xx_eTSEC3,
+	MPC85xx_eTSEC4,
+	MPC85xx_IIC2,
 };
 
+/* Internal interrupts are all Level Sensitive, and Positive Polarity */
+#define MPC85XX_INTERNAL_IRQ_SENSES \
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  0 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  1 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  2 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  3 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  4 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  5 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  6 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  7 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  8 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal  9 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 10 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 11 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 12 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 13 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 14 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 15 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 16 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 17 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 18 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 19 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 20 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 21 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 22 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 23 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 24 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 25 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 26 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 27 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 28 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 29 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 30 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 31 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 32 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 33 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 34 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 35 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 36 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 37 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 38 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 39 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 40 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 41 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 42 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 43 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 44 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 45 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),	/* Internal 46 */	\
+	(IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE)	/* Internal 47 */
+
 #endif /* CONFIG_85xx */
 #endif /* __ASM_MPC85xx_H__ */
 #endif /* __KERNEL__ */
diff --git a/include/asm-ppc/pgtable.h b/include/asm-ppc/pgtable.h
index a38606d..4d4b20c 100644
--- a/include/asm-ppc/pgtable.h
+++ b/include/asm-ppc/pgtable.h
@@ -267,8 +267,6 @@
 #define _PMD_PRESENT_MASK (PAGE_MASK)
 #define _PMD_BAD	(~PAGE_MASK)
 
-#define NUM_TLBCAMS	(16)
-
 #elif defined(CONFIG_8xx)
 /* Definitions for 8xx embedded chips. */
 #define _PAGE_PRESENT	0x0001	/* Page is valid */
diff --git a/include/asm-ppc/ppc_sys.h b/include/asm-ppc/ppc_sys.h
index 24b991c..8ea6245 100644
--- a/include/asm-ppc/ppc_sys.h
+++ b/include/asm-ppc/ppc_sys.h
@@ -27,6 +27,8 @@
 #include <asm/mpc85xx.h>
 #elif defined(CONFIG_PPC_MPC52xx)
 #include <asm/mpc52xx.h>
+#elif defined(CONFIG_MPC10X_BRIDGE)
+#include <asm/mpc10x.h>
 #else
 #error "need definition of ppc_sys_devices"
 #endif
diff --git a/include/asm-ppc/smp.h b/include/asm-ppc/smp.h
index ebfb614..17530c2 100644
--- a/include/asm-ppc/smp.h
+++ b/include/asm-ppc/smp.h
@@ -44,7 +44,7 @@
 #define NO_PROC_ID		0xFF            /* No processor magic marker */
 #define PROC_CHANGE_PENALTY	20
 
-#define smp_processor_id() (current_thread_info()->cpu)
+#define raw_smp_processor_id()	(current_thread_info()->cpu)
 
 extern int __cpu_up(unsigned int cpu);
 
diff --git a/include/asm-ppc64/dma.h b/include/asm-ppc64/dma.h
index d693b80..dfd1f69 100644
--- a/include/asm-ppc64/dma.h
+++ b/include/asm-ppc64/dma.h
@@ -27,6 +27,8 @@
 /* Doesn't really apply... */
 #define MAX_DMA_ADDRESS  (~0UL)
 
+#if !defined(CONFIG_PPC_ISERIES) || defined(CONFIG_PCI)
+
 #define dma_outb	outb
 #define dma_inb		inb
 
@@ -323,4 +325,5 @@
 #else                                                         
 #define isa_dma_bridge_buggy   (0)
 #endif
+#endif	/* !defined(CONFIG_PPC_ISERIES) || defined(CONFIG_PCI) */
 #endif /* _ASM_DMA_H */
diff --git a/include/asm-ppc64/iSeries/HvCall.h b/include/asm-ppc64/iSeries/HvCall.h
index d9a2e74..c3f1947 100644
--- a/include/asm-ppc64/iSeries/HvCall.h
+++ b/include/asm-ppc64/iSeries/HvCall.h
@@ -1,84 +1,36 @@
 /*
  * HvCall.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  */
-
-//===========================================================================
-//
-//	This file contains the "hypervisor call" interface which is used to
-//	drive the hypervisor from the OS.
-//
-//===========================================================================
+/*
+ * This file contains the "hypervisor call" interface which is used to
+ * drive the hypervisor from the OS.
+ */
 #ifndef _HVCALL_H
 #define _HVCALL_H
 
-//-------------------------------------------------------------------
-// Standard Includes
-//-------------------------------------------------------------------
 #include <asm/iSeries/HvCallSc.h>
 #include <asm/iSeries/HvTypes.h>
 #include <asm/paca.h>
 
-/*
-enum HvCall_ReturnCode
-{
-	HvCall_Good		= 0,
-	HvCall_Partial		= 1,
-	HvCall_NotOwned		= 2,
-	HvCall_NotFreed		= 3,
-	HvCall_UnspecifiedError	= 4
-};
-
-enum HvCall_TypeOfSIT
-{
-	HvCall_ReduceOnly	= 0,
-	HvCall_Unconditional	= 1
-};
-
-enum HvCall_TypeOfYield
-{
-	HvCall_YieldTimed	= 0,	// Yield until specified time
-	HvCall_YieldToActive	= 1,	// Yield until all active procs have run
-	HvCall_YieldToProc	= 2	// Yield until the specified processor has run
-};
-
-enum HvCall_InterruptMasks
-{
-	HvCall_MaskIPI		= 0x00000001,
-	HvCall_MaskLpEvent	= 0x00000002,
-	HvCall_MaskLpProd	= 0x00000004,
-	HvCall_MaskTimeout	= 0x00000008
-};
-
-enum HvCall_VaryOffChunkRc
-{
-	HvCall_VaryOffSucceeded		= 0,
-	HvCall_VaryOffWithdrawn		= 1,
-	HvCall_ChunkInLoadArea		= 2,
-	HvCall_ChunkInHPT		= 3,
-	HvCall_ChunkNotAccessible	= 4,
-	HvCall_ChunkInUse		= 5
-};
-*/
-
 /* Type of yield for HvCallBaseYieldProcessor */
-#define HvCall_YieldTimed 	0	// Yield until specified time (tb)
-#define HvCall_YieldToActive	1	// Yield until all active procs have run
-#define HvCall_YieldToProc	2	// Yield until the specified processor has run
+#define HvCall_YieldTimed	0	/* Yield until specified time (tb) */
+#define HvCall_YieldToActive	1	/* Yield until all active procs have run */
+#define HvCall_YieldToProc	2	/* Yield until the specified processor has run */
 
 /* interrupt masks for setEnabledInterrupts */
 #define HvCall_MaskIPI		0x00000001
@@ -86,7 +38,7 @@
 #define HvCall_MaskLpProd	0x00000004
 #define HvCall_MaskTimeout	0x00000008
 
-/* Log buffer formats                       */
+/* Log buffer formats */
 #define HvCall_LogBuffer_ASCII          0
 #define HvCall_LogBuffer_EBCDIC         1
 
@@ -95,7 +47,7 @@
 #define HvCallBaseGetHwPatch				HvCallBase +  2
 #define HvCallBaseReIplSpAttn				HvCallBase +  3
 #define HvCallBaseSetASR				HvCallBase +  4
-#define HvCallBaseSetASRAndRfi				HvCallBase +  5 
+#define HvCallBaseSetASRAndRfi				HvCallBase +  5
 #define HvCallBaseSetIMR				HvCallBase +  6
 #define HvCallBaseSendIPI				HvCallBase +  7
 #define HvCallBaseTerminateMachine			HvCallBase +  8
@@ -115,91 +67,47 @@
 #define HvCallBaseGetLogBufferCodePage			HvCallBase + 22
 #define HvCallBaseGetLogBufferFormat			HvCallBase + 23
 #define HvCallBaseGetLogBufferLength			HvCallBase + 24
-#define HvCallBaseReadLogBuffer 			HvCallBase + 25
+#define HvCallBaseReadLogBuffer				HvCallBase + 25
 #define HvCallBaseSetLogBufferFormatAndCodePage		HvCallBase + 26
-#define HvCallBaseWriteLogBuffer               		HvCallBase + 27
+#define HvCallBaseWriteLogBuffer			HvCallBase + 27
 #define HvCallBaseRouter28				HvCallBase + 28
 #define HvCallBaseRouter29				HvCallBase + 29
 #define HvCallBaseRouter30				HvCallBase + 30
-#define HvCallBaseSetDebugBus 				HvCallBase + 31
+#define HvCallBaseSetDebugBus				HvCallBase + 31
 
-#define HvCallCcSetDABR  				HvCallCc + 7
+#define HvCallCcSetDABR					HvCallCc + 7
 
-//=====================================================================================
-static inline void		HvCall_setVirtualDecr(void)
+static inline void HvCall_setVirtualDecr(void)
 {
-	/* Ignore any error return codes - most likely means that the target value for the
-	 * LP has been increased and this vary off would bring us below the new target. */
+	/*
+	 * Ignore any error return codes - most likely means that the
+	 * target value for the LP has been increased and this vary off
+	 * would bring us below the new target.
+	 */
 	HvCall0(HvCallBaseSetVirtualDecr);
 }
-//=====================================================================
-static inline void		HvCall_yieldProcessor(unsigned typeOfYield, u64 yieldParm)
+
+static inline void HvCall_yieldProcessor(unsigned typeOfYield, u64 yieldParm)
 {
-	HvCall2( HvCallBaseYieldProcessor, typeOfYield, yieldParm );
-}
-//=====================================================================
-static inline void		HvCall_setEnabledInterrupts(u64 enabledInterrupts)
-{
-	HvCall1(HvCallBaseSetEnabledInterrupts,enabledInterrupts);
+	HvCall2(HvCallBaseYieldProcessor, typeOfYield, yieldParm);
 }
 
-//=====================================================================
-static inline void		HvCall_clearLogBuffer(HvLpIndex lpindex)
+static inline void HvCall_setEnabledInterrupts(u64 enabledInterrupts)
 {
-	HvCall1(HvCallBaseClearLogBuffer,lpindex);
+	HvCall1(HvCallBaseSetEnabledInterrupts, enabledInterrupts);
 }
 
-//=====================================================================
-static inline u32  		HvCall_getLogBufferCodePage(HvLpIndex lpindex)
+static inline void HvCall_setLogBufferFormatAndCodepage(int format,
+		u32 codePage)
 {
-	u32 retVal = HvCall1(HvCallBaseGetLogBufferCodePage,lpindex);
-	return retVal;
+	HvCall2(HvCallBaseSetLogBufferFormatAndCodePage, format, codePage);
 }
 
-//=====================================================================
-static inline int  		HvCall_getLogBufferFormat(HvLpIndex lpindex)
-{
-	int retVal = HvCall1(HvCallBaseGetLogBufferFormat,lpindex);
-	return retVal;
-}
+extern void HvCall_writeLogBuffer(const void *buffer, u64 bufLen);
 
-//=====================================================================
-static inline u32  		HvCall_getLogBufferLength(HvLpIndex lpindex)
+static inline void HvCall_sendIPI(struct paca_struct *targetPaca)
 {
-	u32 retVal = HvCall1(HvCallBaseGetLogBufferLength,lpindex);
-	return retVal;
-}
-
-//=====================================================================
-static inline void  		HvCall_setLogBufferFormatAndCodepage(int format, u32 codePage)
-{
-	HvCall2(HvCallBaseSetLogBufferFormatAndCodePage,format, codePage);
-}
-
-//=====================================================================
-int HvCall_readLogBuffer(HvLpIndex lpindex, void *buffer, u64 bufLen);
-void HvCall_writeLogBuffer(const void *buffer, u64 bufLen);
-
-//=====================================================================
-static inline void		HvCall_sendIPI(struct paca_struct * targetPaca)
-{
-	HvCall1( HvCallBaseSendIPI, targetPaca->paca_index );
-}
-
-//=====================================================================
-static inline void		HvCall_terminateMachineSrc(void)
-{
-	HvCall0( HvCallBaseTerminateMachineSrc );
-}
-
-static inline void HvCall_setDABR(unsigned long val)
-{
-	HvCall1(HvCallCcSetDABR, val);
-}
-
-static inline void HvCall_setDebugBus(unsigned long val)
-{
-	HvCall1(HvCallBaseSetDebugBus, val);
+	HvCall1(HvCallBaseSendIPI, targetPaca->paca_index);
 }
 
 #endif /* _HVCALL_H */
diff --git a/include/asm-ppc64/iSeries/HvCallCfg.h b/include/asm-ppc64/iSeries/HvCallCfg.h
deleted file mode 100644
index 9f40f16..0000000
--- a/include/asm-ppc64/iSeries/HvCallCfg.h
+++ /dev/null
@@ -1,213 +0,0 @@
-/*
- * HvCallCfg.h
- * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- * 
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
- */
-
-//=====================================================================================
-//
-//	This file contains the "hypervisor call" interface which is used to
-//	drive the hypervisor from the OS.
-//
-//=====================================================================================
-#ifndef _HVCALLCFG_H
-#define _HVCALLCFG_H
-
-//-------------------------------------------------------------------
-// Standard Includes
-//-------------------------------------------------------------------
-#include <asm/iSeries/HvCallSc.h>
-#include <asm/iSeries/HvTypes.h>
-
-//-------------------------------------------------------------------------------------
-// Constants
-//-------------------------------------------------------------------------------------
-
-enum HvCallCfg_ReqQual
-{
-	HvCallCfg_Cur	= 0,
-	HvCallCfg_Init	= 1,
-	HvCallCfg_Max	= 2,
-	HvCallCfg_Min	= 3
-};
-
-#define HvCallCfgGetLps					HvCallCfg +  0
-#define HvCallCfgGetActiveLpMap				HvCallCfg +  1
-#define HvCallCfgGetLpVrmIndex				HvCallCfg +  2
-#define HvCallCfgGetLpMinSupportedPlicVrmIndex		HvCallCfg +  3
-#define HvCallCfgGetLpMinCompatablePlicVrmIndex		HvCallCfg +  4
-#define HvCallCfgGetLpVrmName				HvCallCfg +  5 
-#define HvCallCfgGetSystemPhysicalProcessors		HvCallCfg +  6
-#define HvCallCfgGetPhysicalProcessors			HvCallCfg +  7
-#define HvCallCfgGetSystemMsChunks			HvCallCfg +  8
-#define HvCallCfgGetMsChunks				HvCallCfg +  9
-#define HvCallCfgGetInteractivePercentage		HvCallCfg + 10
-#define HvCallCfgIsBusDedicated				HvCallCfg + 11
-#define HvCallCfgGetBusOwner				HvCallCfg + 12
-#define HvCallCfgGetBusAllocation			HvCallCfg + 13
-#define HvCallCfgGetBusUnitOwner			HvCallCfg + 14
-#define HvCallCfgGetBusUnitAllocation			HvCallCfg + 15
-#define HvCallCfgGetVirtualBusPool			HvCallCfg + 16
-#define HvCallCfgGetBusUnitInterruptProc		HvCallCfg + 17
-#define HvCallCfgGetConfiguredBusUnitsForIntProc	HvCallCfg + 18
-#define HvCallCfgGetRioSanBusPool			HvCallCfg + 19
-#define HvCallCfgGetSharedPoolIndex			HvCallCfg + 20
-#define HvCallCfgGetSharedProcUnits			HvCallCfg + 21
-#define HvCallCfgGetNumProcsInSharedPool		HvCallCfg + 22
-#define HvCallCfgRouter23				HvCallCfg + 23
-#define HvCallCfgRouter24				HvCallCfg + 24
-#define HvCallCfgRouter25				HvCallCfg + 25
-#define HvCallCfgRouter26				HvCallCfg + 26
-#define HvCallCfgRouter27				HvCallCfg + 27
-#define HvCallCfgGetMinRuntimeMsChunks			HvCallCfg + 28
-#define HvCallCfgSetMinRuntimeMsChunks			HvCallCfg + 29
-#define HvCallCfgGetVirtualLanIndexMap			HvCallCfg + 30
-#define HvCallCfgGetLpExecutionMode			HvCallCfg + 31
-#define HvCallCfgGetHostingLpIndex 			HvCallCfg + 32
-
-//====================================================================
-static inline HvLpIndex	HvCallCfg_getLps(void)
-{
-	HvLpIndex retVal = HvCall0(HvCallCfgGetLps);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//====================================================================
-static inline int		HvCallCfg_isBusDedicated(u64 busIndex)
-{
-	int retVal = HvCall1(HvCallCfgIsBusDedicated,busIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//====================================================================
-static inline HvLpIndex	HvCallCfg_getBusOwner(u64 busIndex)
-{
-	HvLpIndex retVal = HvCall1(HvCallCfgGetBusOwner,busIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//====================================================================
-static inline HvLpIndexMap	HvCallCfg_getBusAllocation(u64 busIndex)
-{
-	HvLpIndexMap retVal = HvCall1(HvCallCfgGetBusAllocation,busIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//====================================================================
-static inline HvLpIndexMap	HvCallCfg_getActiveLpMap(void)
-{
-	HvLpIndexMap retVal = HvCall0(HvCallCfgGetActiveLpMap);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//====================================================================
-static inline HvLpVirtualLanIndexMap	HvCallCfg_getVirtualLanIndexMap(HvLpIndex lp)
-{
-	// This is a new function in V5R1 so calls to this on older 
-	// hypervisors will return -1
-	u64 retVal = HvCall1(HvCallCfgGetVirtualLanIndexMap, lp);
-	if(retVal == -1)
-		retVal = 0;
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_getSystemMsChunks(void)
-{
-	u64 retVal = HvCall0(HvCallCfgGetSystemMsChunks);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_getMsChunks(HvLpIndex lp,enum HvCallCfg_ReqQual qual)
-{
-	u64 retVal = HvCall2(HvCallCfgGetMsChunks,lp,qual);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_getMinRuntimeMsChunks(HvLpIndex lp)
-{
-	// NOTE: This function was added in v5r1 so older hypervisors will return a -1 value
-	u64 retVal = HvCall1(HvCallCfgGetMinRuntimeMsChunks,lp);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_setMinRuntimeMsChunks(u64 chunks)
-{
-	u64 retVal = HvCall1(HvCallCfgSetMinRuntimeMsChunks,chunks);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_getSystemPhysicalProcessors(void)
-{
-	u64 retVal = HvCall0(HvCallCfgGetSystemPhysicalProcessors);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_getPhysicalProcessors(HvLpIndex lp,enum HvCallCfg_ReqQual qual)
-{
-	u64 retVal = HvCall2(HvCallCfgGetPhysicalProcessors,lp,qual);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//===================================================================
-static inline u64		HvCallCfg_getConfiguredBusUnitsForInterruptProc(HvLpIndex lp,
-										u16 hvLogicalProcIndex)
-{
-	u64 retVal = HvCall2(HvCallCfgGetConfiguredBusUnitsForIntProc,lp,hvLogicalProcIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-
-}
-//==================================================================
-static inline HvLpSharedPoolIndex	HvCallCfg_getSharedPoolIndex(HvLpIndex lp)
-{
-	HvLpSharedPoolIndex retVal =
-		HvCall1(HvCallCfgGetSharedPoolIndex,lp);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-
-}
-//==================================================================
-static inline u64	HvCallCfg_getSharedProcUnits(HvLpIndex lp,enum HvCallCfg_ReqQual qual)
-{
-	u64 retVal = HvCall2(HvCallCfgGetSharedProcUnits,lp,qual);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-
-}
-//==================================================================
-static inline u64	HvCallCfg_getNumProcsInSharedPool(HvLpSharedPoolIndex sPI)
-{
-	u16 retVal = HvCall1(HvCallCfgGetNumProcsInSharedPool,sPI);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-
-}
-//==================================================================
-static inline HvLpIndex	HvCallCfg_getHostingLpIndex(HvLpIndex lp)
-{
-	u64 retVal = HvCall1(HvCallCfgGetHostingLpIndex,lp);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-
-}
-
-#endif /* _HVCALLCFG_H */
diff --git a/include/asm-ppc64/iSeries/HvCallEvent.h b/include/asm-ppc64/iSeries/HvCallEvent.h
index 191ddce..5d9a327 100644
--- a/include/asm-ppc64/iSeries/HvCallEvent.h
+++ b/include/asm-ppc64/iSeries/HvCallEvent.h
@@ -1,32 +1,28 @@
 /*
  * HvCallEvent.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  */
-
 /*
- *	This file contains the "hypervisor call" interface which is used to
- *	drive the hypervisor from the OS.
+ * This file contains the "hypervisor call" interface which is used to
+ * drive the hypervisor from the OS.
  */
 #ifndef _HVCALLEVENT_H
 #define _HVCALLEVENT_H
 
-/*
- * Standard Includes
- */
 #include <asm/iSeries/HvCallSc.h>
 #include <asm/iSeries/HvTypes.h>
 #include <asm/abs_addr.h>
@@ -71,7 +67,7 @@
 #define HvCallEventCloseLpEventPath			HvCallEvent +  2
 #define HvCallEventDmaBufList				HvCallEvent +  3
 #define HvCallEventDmaSingle				HvCallEvent +  4
-#define HvCallEventDmaToSp				HvCallEvent +  5 
+#define HvCallEventDmaToSp				HvCallEvent +  5
 #define HvCallEventGetOverflowLpEvents			HvCallEvent +  6
 #define HvCallEventGetSourceLpInstanceId		HvCallEvent +  7
 #define HvCallEventGetTargetLpInstanceId		HvCallEvent +  8
@@ -85,14 +81,12 @@
 
 static inline void HvCallEvent_getOverflowLpEvents(u8 queueIndex)
 {
-	HvCall1(HvCallEventGetOverflowLpEvents,queueIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	HvCall1(HvCallEventGetOverflowLpEvents, queueIndex);
 }
 
 static inline void HvCallEvent_setInterLpQueueIndex(u8 queueIndex)
 {
-	HvCall1(HvCallEventSetInterLpQueueIndex,queueIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	HvCall1(HvCallEventSetInterLpQueueIndex, queueIndex);
 }
 
 static inline void HvCallEvent_setLpEventStack(u8 queueIndex,
@@ -103,7 +97,6 @@
 	abs_addr = virt_to_abs(eventStackAddr);
 	HvCall3(HvCallEventSetLpEventStack, queueIndex, abs_addr,
 			eventStackSize);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
 }
 
 static inline void HvCallEvent_setLpEventQueueInterruptProc(u8 queueIndex,
@@ -111,22 +104,18 @@
 {
 	HvCall2(HvCallEventSetLpEventQueueInterruptProc, queueIndex,
 			lpLogicalProcIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
 }
 
 static inline HvLpEvent_Rc HvCallEvent_signalLpEvent(struct HvLpEvent *event)
 {
 	u64 abs_addr;
-	HvLpEvent_Rc retVal;
 
 #ifdef DEBUG_SENDEVENT
 	printk("HvCallEvent_signalLpEvent: *event = %016lx\n ",
 			(unsigned long)event);
 #endif
 	abs_addr = virt_to_abs(event);
-	retVal = (HvLpEvent_Rc)HvCall1(HvCallEventSignalLpEvent, abs_addr);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall1(HvCallEventSignalLpEvent, abs_addr);
 }
 
 static inline HvLpEvent_Rc HvCallEvent_signalLpEventFast(HvLpIndex targetLp,
@@ -136,9 +125,7 @@
 		u64 eventData1, u64 eventData2, u64 eventData3,
 		u64 eventData4, u64 eventData5)
 {
-	HvLpEvent_Rc retVal;
-
-	// Pack the misc bits into a single Dword to pass to PLIC
+	/* Pack the misc bits into a single Dword to pass to PLIC */
 	union {
 		struct HvCallEvent_PackedParms	parms;
 		u64		dword;
@@ -152,67 +139,49 @@
 	packed.parms.xSourceInstId	= sourceInstanceId;
 	packed.parms.xTargetInstId	= targetInstanceId;
 
-	retVal = (HvLpEvent_Rc)HvCall7(HvCallEventSignalLpEventParms,
-			packed.dword, correlationToken, eventData1,eventData2,
-			eventData3,eventData4, eventData5);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall7(HvCallEventSignalLpEventParms, packed.dword,
+			correlationToken, eventData1, eventData2,
+			eventData3, eventData4, eventData5);
 }
 
 static inline HvLpEvent_Rc HvCallEvent_ackLpEvent(struct HvLpEvent *event)
 {
 	u64 abs_addr;
-	HvLpEvent_Rc retVal;
 
 	abs_addr = virt_to_abs(event);
-	retVal = (HvLpEvent_Rc)HvCall1(HvCallEventAckLpEvent, abs_addr);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall1(HvCallEventAckLpEvent, abs_addr);
 }
 
 static inline HvLpEvent_Rc HvCallEvent_cancelLpEvent(struct HvLpEvent *event)
 {
 	u64 abs_addr;
-	HvLpEvent_Rc retVal;
 
 	abs_addr = virt_to_abs(event);
-	retVal = (HvLpEvent_Rc)HvCall1(HvCallEventCancelLpEvent, abs_addr);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall1(HvCallEventCancelLpEvent, abs_addr);
 }
 
 static inline HvLpInstanceId HvCallEvent_getSourceLpInstanceId(
 		HvLpIndex targetLp, HvLpEvent_Type type)
 {
-	HvLpInstanceId retVal;	
-
-	retVal = HvCall2(HvCallEventGetSourceLpInstanceId, targetLp, type);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall2(HvCallEventGetSourceLpInstanceId, targetLp, type);
 }
 
 static inline HvLpInstanceId HvCallEvent_getTargetLpInstanceId(
 		HvLpIndex targetLp, HvLpEvent_Type type)
 {
-	HvLpInstanceId retVal;	
-
-	retVal = HvCall2(HvCallEventGetTargetLpInstanceId, targetLp, type);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall2(HvCallEventGetTargetLpInstanceId, targetLp, type);
 }
 
 static inline void HvCallEvent_openLpEventPath(HvLpIndex targetLp,
 		HvLpEvent_Type type)
 {
 	HvCall2(HvCallEventOpenLpEventPath, targetLp, type);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
 }
 
 static inline void HvCallEvent_closeLpEventPath(HvLpIndex targetLp,
 		HvLpEvent_Type type)
 {
 	HvCall2(HvCallEventCloseLpEventPath, targetLp, type);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
 }
 
 static inline HvLpDma_Rc HvCallEvent_dmaBufList(HvLpEvent_Type type,
@@ -224,8 +193,7 @@
 		/* Do these need to be converted to absolute addresses? */
 		u64 localBufList, u64 remoteBufList, u32 transferLength)
 {
-	HvLpDma_Rc retVal;
-	// Pack the misc bits into a single Dword to pass to PLIC
+	/* Pack the misc bits into a single Dword to pass to PLIC */
 	union {
 		struct HvCallEvent_PackedDmaParms	parms;
 		u64		dword;
@@ -241,11 +209,8 @@
 	packed.parms.xLocalInstId	= localInstanceId;
 	packed.parms.xRemoteInstId	= remoteInstanceId;
 
-	retVal = (HvLpDma_Rc)HvCall4(HvCallEventDmaBufList,
-			packed.dword, localBufList, remoteBufList,
-			transferLength);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall4(HvCallEventDmaBufList, packed.dword, localBufList,
+			remoteBufList, transferLength);
 }
 
 static inline HvLpDma_Rc HvCallEvent_dmaSingle(HvLpEvent_Type type,
@@ -256,8 +221,7 @@
 		HvLpDma_AddressType remoteAddressType,
 		u64 localAddrOrTce, u64 remoteAddrOrTce, u32 transferLength)
 {
-	HvLpDma_Rc retVal;
-	// Pack the misc bits into a single Dword to pass to PLIC
+	/* Pack the misc bits into a single Dword to pass to PLIC */
 	union {
 		struct HvCallEvent_PackedDmaParms	parms;
 		u64		dword;
@@ -273,25 +237,17 @@
 	packed.parms.xLocalInstId	= localInstanceId;
 	packed.parms.xRemoteInstId	= remoteInstanceId;
 
-	retVal = (HvLpDma_Rc)HvCall4(HvCallEventDmaSingle,
-			packed.dword, localAddrOrTce, remoteAddrOrTce,
-			transferLength);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return (HvLpDma_Rc)HvCall4(HvCallEventDmaSingle, packed.dword,
+			localAddrOrTce, remoteAddrOrTce, transferLength);
 }
 
-static inline HvLpDma_Rc HvCallEvent_dmaToSp(void* local, u32 remote,
+static inline HvLpDma_Rc HvCallEvent_dmaToSp(void *local, u32 remote,
 		u32 length, HvLpDma_Direction dir)
 {
 	u64 abs_addr;
-	HvLpDma_Rc retVal;
 
 	abs_addr = virt_to_abs(local);
-	retVal = (HvLpDma_Rc)HvCall4(HvCallEventDmaToSp, abs_addr, remote,
-			length, dir);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall4(HvCallEventDmaToSp, abs_addr, remote, length, dir);
 }
 
-
 #endif /* _HVCALLEVENT_H */
diff --git a/include/asm-ppc64/iSeries/HvCallHpt.h b/include/asm-ppc64/iSeries/HvCallHpt.h
index da76987..66f3822 100644
--- a/include/asm-ppc64/iSeries/HvCallHpt.h
+++ b/include/asm-ppc64/iSeries/HvCallHpt.h
@@ -1,17 +1,17 @@
 /*
  * HvCallHpt.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,21 +19,15 @@
 #ifndef _HVCALLHPT_H
 #define _HVCALLHPT_H
 
-//============================================================================
-//
-//	This file contains the "hypervisor call" interface which is used to
-//	drive the hypervisor from the OS.
-//
-//============================================================================
+/*
+ * This file contains the "hypervisor call" interface which is used to
+ * drive the hypervisor from the OS.
+ */
 
 #include <asm/iSeries/HvCallSc.h>
 #include <asm/iSeries/HvTypes.h>
 #include <asm/mmu.h>
 
-//-----------------------------------------------------------------------------
-// Constants
-//-----------------------------------------------------------------------------
-
 #define HvCallHptGetHptAddress		HvCallHpt +  0
 #define HvCallHptGetHptPages		HvCallHpt +  1
 #define HvCallHptSetPp			HvCallHpt +  5
@@ -47,81 +41,63 @@
 #define HvCallHptInvalidateSetSwBitsGet HvCallHpt + 18
 
 
-//============================================================================
-static inline u64		HvCallHpt_getHptAddress(void)
+static inline u64 HvCallHpt_getHptAddress(void)
 {
-	u64 retval = HvCall0(HvCallHptGetHptAddress);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retval;
+	return HvCall0(HvCallHptGetHptAddress);
 }
-//============================================================================
-static inline u64		HvCallHpt_getHptPages(void)
-{	
-	u64 retval = HvCall0(HvCallHptGetHptPages);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retval;
-}
-//=============================================================================
-static inline void		HvCallHpt_setPp(u32 hpteIndex, u8 value)
+
+static inline u64 HvCallHpt_getHptPages(void)
 {
-	HvCall2( HvCallHptSetPp, hpteIndex, value );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	return HvCall0(HvCallHptGetHptPages);
 }
-//=============================================================================
-static inline void		HvCallHpt_setSwBits(u32 hpteIndex, u8 bitson, u8 bitsoff )
+
+static inline void HvCallHpt_setPp(u32 hpteIndex, u8 value)
 {
-	HvCall3( HvCallHptSetSwBits, hpteIndex, bitson, bitsoff );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	HvCall2(HvCallHptSetPp, hpteIndex, value);
 }
-//=============================================================================
-static inline void		HvCallHpt_invalidateNoSyncICache(u32 hpteIndex)
-						
+
+static inline void HvCallHpt_setSwBits(u32 hpteIndex, u8 bitson, u8 bitsoff)
 {
-	HvCall1( HvCallHptInvalidateNoSyncICache, hpteIndex );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	HvCall3(HvCallHptSetSwBits, hpteIndex, bitson, bitsoff);
 }
-//=============================================================================
-static inline u64		HvCallHpt_invalidateSetSwBitsGet(u32 hpteIndex, u8 bitson, u8 bitsoff )
-						
+
+static inline void HvCallHpt_invalidateNoSyncICache(u32 hpteIndex)
+{
+	HvCall1(HvCallHptInvalidateNoSyncICache, hpteIndex);
+}
+
+static inline u64 HvCallHpt_invalidateSetSwBitsGet(u32 hpteIndex, u8 bitson,
+		u8 bitsoff)
 {
 	u64 compressedStatus;
-	compressedStatus = HvCall4( HvCallHptInvalidateSetSwBitsGet, hpteIndex, bitson, bitsoff, 1 );
-	HvCall1( HvCallHptInvalidateNoSyncICache, hpteIndex );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+
+	compressedStatus = HvCall4(HvCallHptInvalidateSetSwBitsGet,
+			hpteIndex, bitson, bitsoff, 1);
+	HvCall1(HvCallHptInvalidateNoSyncICache, hpteIndex);
 	return compressedStatus;
 }
-//=============================================================================
-static inline u64		HvCallHpt_findValid( HPTE *hpte, u64 vpn )
+
+static inline u64 HvCallHpt_findValid(HPTE *hpte, u64 vpn)
 {
-	u64 retIndex = HvCall3Ret16( HvCallHptFindValid, hpte, vpn, 0, 0 );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retIndex;
-}
-//=============================================================================
-static inline u64		HvCallHpt_findNextValid( HPTE *hpte, u32 hpteIndex, u8 bitson, u8 bitsoff )
-{
-	u64 retIndex = HvCall3Ret16( HvCallHptFindNextValid, hpte, hpteIndex, bitson, bitsoff );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retIndex;
-}
-//=============================================================================
-static inline void		HvCallHpt_get( HPTE *hpte, u32 hpteIndex )
-{
-	HvCall2Ret16( HvCallHptGet, hpte, hpteIndex, 0 );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-}
-//============================================================================
-static inline void		HvCallHpt_addValidate( u32 hpteIndex,
-						       u32 hBit,
-						       HPTE *hpte )
-						
-{
-	HvCall4( HvCallHptAddValidate, hpteIndex,
-		 hBit, (*((u64 *)hpte)), (*(((u64 *)hpte)+1)) );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	return HvCall3Ret16(HvCallHptFindValid, hpte, vpn, 0, 0);
 }
 
+static inline u64 HvCallHpt_findNextValid(HPTE *hpte, u32 hpteIndex,
+		u8 bitson, u8 bitsoff)
+{
+	return HvCall3Ret16(HvCallHptFindNextValid, hpte, hpteIndex,
+			bitson, bitsoff);
+}
 
-//=============================================================================
+static inline void HvCallHpt_get(HPTE *hpte, u32 hpteIndex)
+{
+	HvCall2Ret16(HvCallHptGet, hpte, hpteIndex, 0);
+}
+
+static inline void HvCallHpt_addValidate(u32 hpteIndex, u32 hBit, HPTE *hpte)
+{
+	HvCall4(HvCallHptAddValidate, hpteIndex, hBit, (*((u64 *)hpte)),
+			(*(((u64 *)hpte)+1)));
+}
 
 #endif /* _HVCALLHPT_H */
diff --git a/include/asm-ppc64/iSeries/HvCallPci.h b/include/asm-ppc64/iSeries/HvCallPci.h
index 6887b61..c8d675c 100644
--- a/include/asm-ppc64/iSeries/HvCallPci.h
+++ b/include/asm-ppc64/iSeries/HvCallPci.h
@@ -1,26 +1,26 @@
-/************************************************************************/
-/* Provides the Hypervisor PCI calls for iSeries Linux Parition.        */
-/* Copyright (C) 2001  <Wayne G Holm> <IBM Corporation>                 */
-/*                                                                      */
-/* This program is free software; you can redistribute it and/or modify */
-/* it under the terms of the GNU General Public License as published by */
-/* the Free Software Foundation; either version 2 of the License, or    */
-/* (at your option) any later version.                                  */
-/*                                                                      */
-/* This program is distributed in the hope that it will be useful,      */ 
-/* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
-/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
-/* GNU General Public License for more details.                         */
-/*                                                                      */
-/* You should have received a copy of the GNU General Public License    */ 
-/* along with this program; if not, write to the:                       */
-/* Free Software Foundation, Inc.,                                      */ 
-/* 59 Temple Place, Suite 330,                                          */ 
-/* Boston, MA  02111-1307  USA                                          */
-/************************************************************************/
-/* Change Activity:                                                     */
-/*   Created, Jan 9, 2001                                               */
-/************************************************************************/
+/*
+ * Provides the Hypervisor PCI calls for iSeries Linux Parition.
+ * Copyright (C) 2001  <Wayne G Holm> <IBM Corporation>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the:
+ * Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330,
+ * Boston, MA  02111-1307  USA
+ *
+ * Change Activity:
+ *   Created, Jan 9, 2001
+ */
 
 #ifndef _HVCALLPCI_H
 #define _HVCALLPCI_H
@@ -34,8 +34,8 @@
  */
 struct HvCallPci_DsaAddr {
 	u16		busNumber;		/* PHB index? */
-	u8		subBusNumber; 		/* PCI bus number? */
-	u8		deviceId;     		/* device and function? */
+	u8		subBusNumber;		/* PCI bus number? */
+	u8		deviceId;		/* device and function? */
 	u8		barNumber;
 	u8		reserved[3];
 };
@@ -52,34 +52,37 @@
 
 enum HvCallPci_DeviceType {
 	HvCallPci_NodeDevice	= 1,
-	HvCallPci_SpDevice	= 2,	
-	HvCallPci_IopDevice     = 3,	
-	HvCallPci_BridgeDevice	= 4,	
-	HvCallPci_MultiFunctionDevice = 5,	
-	HvCallPci_IoaDevice	= 6	
+	HvCallPci_SpDevice	= 2,
+	HvCallPci_IopDevice     = 3,
+	HvCallPci_BridgeDevice	= 4,
+	HvCallPci_MultiFunctionDevice = 5,
+	HvCallPci_IoaDevice	= 6
 };
 
 
 struct HvCallPci_DeviceInfo {
-	u32	deviceType;		// See DeviceType enum for values
+	u32	deviceType;		/* See DeviceType enum for values */
 };
-    
+
 struct HvCallPci_BusUnitInfo {
-	u32	sizeReturned;		// length of data returned
-	u32	deviceType;		// see DeviceType enum for values
+	u32	sizeReturned;		/* length of data returned */
+	u32	deviceType;		/* see DeviceType enum for values */
 };
 
 struct HvCallPci_BridgeInfo {
-	struct HvCallPci_BusUnitInfo busUnitInfo;  // Generic bus unit info
-	u8		subBusNumber;		// Bus number of secondary bus
-	u8		maxAgents;		// Max idsels on secondary bus
-        u8              maxSubBusNumber;        // Max Sub Bus
-	u8		logicalSlotNumber;	// Logical Slot Number for IOA 
+	struct HvCallPci_BusUnitInfo busUnitInfo;  /* Generic bus unit info */
+	u8		subBusNumber;	/* Bus number of secondary bus */
+	u8		maxAgents;	/* Max idsels on secondary bus */
+        u8              maxSubBusNumber; /* Max Sub Bus */
+	u8		logicalSlotNumber; /* Logical Slot Number for IOA */
 };
-    
 
-//  Maximum BusUnitInfo buffer size.  Provided for clients so they can allocate
-//  a buffer big enough for any type of bus unit.  Increase as needed.
+
+/*
+ * Maximum BusUnitInfo buffer size.  Provided for clients so
+ * they can allocate a buffer big enough for any type of bus
+ * unit.  Increase as needed.
+ */
 enum {HvCallPci_MaxBusUnitInfoSize = 128};
 
 struct HvCallPci_BarParms {
@@ -89,12 +92,12 @@
 	u64		protectStart;
 	u64		protectEnd;
 	u64		relocationOffset;
-	u64		pciAddress;		
+	u64		pciAddress;
 	u64		reserved[3];
-};					
+};
 
 enum HvCallPci_VpdType {
-	HvCallPci_BusVpd		= 1,
+	HvCallPci_BusVpd	= 1,
 	HvCallPci_BusAdapterVpd	= 2
 };
 
@@ -123,15 +126,13 @@
 #define HvCallPciUnmaskInterrupts	HvCallPci + 49
 #define HvCallPciGetBusUnitInfo		HvCallPci + 50
 
-//============================================================================
 static inline u64 HvCallPci_configLoad8(u16 busNumber, u8 subBusNumber,
-					u8 deviceId, u32 offset,
-					u8 *value)
+		u8 deviceId, u32 offset, u8 *value)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumber;
 	dsa.subBusNumber = subBusNumber;
@@ -139,21 +140,18 @@
 
 	HvCall3Ret16(HvCallPciConfigLoad8, &retVal, *(u64 *)&dsa, offset, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*value = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
+
 static inline u64 HvCallPci_configLoad16(u16 busNumber, u8 subBusNumber,
-					 u8 deviceId, u32 offset,
-					 u16 *value)
+		u8 deviceId, u32 offset, u16 *value)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumber;
 	dsa.subBusNumber = subBusNumber;
@@ -161,21 +159,18 @@
 
 	HvCall3Ret16(HvCallPciConfigLoad16, &retVal, *(u64 *)&dsa, offset, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*value = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_configLoad32(u16 busNumber, u8 subBusNumber,
-					      u8 deviceId, u32 offset,
-					      u32 *value)
+
+static inline u64 HvCallPci_configLoad32(u16 busNumber, u8 subBusNumber,
+		u8 deviceId, u32 offset, u32 *value)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumber;
 	dsa.subBusNumber = subBusNumber;
@@ -183,84 +178,61 @@
 
 	HvCall3Ret16(HvCallPciConfigLoad32, &retVal, *(u64 *)&dsa, offset, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*value = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_configStore8(u16 busNumber, u8 subBusNumber,
-					      u8 deviceId, u32 offset,
-					      u8  value)
+
+static inline u64 HvCallPci_configStore8(u16 busNumber, u8 subBusNumber,
+		u8 deviceId, u32 offset, u8 value)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumber;
 	dsa.subBusNumber = subBusNumber;
 	dsa.deviceId = deviceId;
 
-	retVal = HvCall4(HvCallPciConfigStore8, *(u64 *)&dsa, offset, value, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciConfigStore8, *(u64 *)&dsa, offset, value, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_configStore16(u16 busNumber, u8 subBusNumber,
-					      u8 deviceId, u32 offset,
-					      u16  value)
+
+static inline u64 HvCallPci_configStore16(u16 busNumber, u8 subBusNumber,
+		u8 deviceId, u32 offset, u16 value)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumber;
 	dsa.subBusNumber = subBusNumber;
 	dsa.deviceId = deviceId;
 
-	retVal = HvCall4(HvCallPciConfigStore16, *(u64 *)&dsa, offset, value, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciConfigStore16, *(u64 *)&dsa, offset, value, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_configStore32(u16 busNumber, u8 subBusNumber,
-					      u8 deviceId, u32 offset,
-					      u32  value)
+
+static inline u64 HvCallPci_configStore32(u16 busNumber, u8 subBusNumber,
+		u8 deviceId, u32 offset, u32 value)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumber;
 	dsa.subBusNumber = subBusNumber;
 	dsa.deviceId = deviceId;
 
-	retVal = HvCall4(HvCallPciConfigStore32, *(u64 *)&dsa, offset, value, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciConfigStore32, *(u64 *)&dsa, offset, value, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_barLoad8(u16	busNumberParm,
-					   u8		subBusParm,
-					   u8		deviceIdParm,
-					   u8		barNumberParm,
-					   u64		offsetParm,
-					   u8*		valueParm)
+
+static inline u64 HvCallPci_barLoad8(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u8 *valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
@@ -269,24 +241,19 @@
 
 	HvCall3Ret16(HvCallPciBarLoad8, &retVal, *(u64 *)&dsa, offsetParm, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*valueParm = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_barLoad16(u16	busNumberParm,
-					   u8		subBusParm,
-					   u8		deviceIdParm,
-					   u8		barNumberParm,
-					   u64		offsetParm,
-					   u16*		valueParm)
+
+static inline u64 HvCallPci_barLoad16(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u16 *valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
@@ -295,24 +262,19 @@
 
 	HvCall3Ret16(HvCallPciBarLoad16, &retVal, *(u64 *)&dsa, offsetParm, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*valueParm = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_barLoad32(u16	busNumberParm,
-					   u8		subBusParm,
-					   u8		deviceIdParm,
-					   u8		barNumberParm,
-					   u64		offsetParm,
-					   u32*		valueParm)
+
+static inline u64 HvCallPci_barLoad32(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u32 *valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
@@ -321,24 +283,19 @@
 
 	HvCall3Ret16(HvCallPciBarLoad32, &retVal, *(u64 *)&dsa, offsetParm, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*valueParm = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_barLoad64(u16	busNumberParm,
-					   u8		subBusParm,
-					   u8		deviceIdParm,
-					   u8		barNumberParm,
-					   u64		offsetParm,
-					   u64*		valueParm)
+
+static inline u64 HvCallPci_barLoad64(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u64 *valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
 
-	*((u64*)&dsa) = 0;				
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
@@ -347,112 +304,81 @@
 
 	HvCall3Ret16(HvCallPciBarLoad64, &retVal, *(u64 *)&dsa, offsetParm, 0);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	*valueParm = retVal.value;
 
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_barStore8(u16	busNumberParm,
-					    u8		subBusParm,
-					    u8		deviceIdParm,
-					    u8		barNumberParm,
-					    u64		offsetParm,
-					    u8		valueParm)
+
+static inline u64 HvCallPci_barStore8(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u8 valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
 	*((u64*)&dsa) = 0;
-				
+
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 	dsa.barNumber = barNumberParm;
 
-	retVal = HvCall4(HvCallPciBarStore8, *(u64 *)&dsa, offsetParm, valueParm, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciBarStore8, *(u64 *)&dsa, offsetParm,
+			valueParm, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_barStore16(u16	busNumberParm,
-					     u8		subBusParm,
-					     u8		deviceIdParm,
-					     u8		barNumberParm,
-					     u64	offsetParm,
-					     u16	valueParm)
+
+static inline u64 HvCallPci_barStore16(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u16 valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
 	*((u64*)&dsa) = 0;
-				
+
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 	dsa.barNumber = barNumberParm;
 
-	retVal = HvCall4(HvCallPciBarStore16, *(u64 *)&dsa, offsetParm, valueParm, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciBarStore16, *(u64 *)&dsa, offsetParm,
+			valueParm, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_barStore32(u16	busNumberParm,
-					     u8		subBusParm,
-					     u8		deviceIdParm,
-					     u8		barNumberParm,
-					     u64	offsetParm,
-					     u32	valueParm)
+
+static inline u64 HvCallPci_barStore32(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u32 valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
 	*((u64*)&dsa) = 0;
-				
+
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 	dsa.barNumber = barNumberParm;
 
-	retVal = HvCall4(HvCallPciBarStore32, *(u64 *)&dsa, offsetParm, valueParm, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciBarStore32, *(u64 *)&dsa, offsetParm,
+			valueParm, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_barStore64(u16	busNumberParm,
-					     u8		subBusParm,
-					     u8		deviceIdParm,
-					     u8		barNumberParm,
-					     u64	offsetParm,
-					     u64	valueParm)
+
+static inline u64 HvCallPci_barStore64(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 offsetParm,
+		u64 valueParm)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
 	*((u64*)&dsa) = 0;
-				
+
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 	dsa.barNumber = barNumberParm;
 
-	retVal = HvCall4(HvCallPciBarStore64, *(u64 *)&dsa, offsetParm, valueParm, 0);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall4(HvCallPciBarStore64, *(u64 *)&dsa, offsetParm,
+			valueParm, 0);
 }
-//============================================================================
-static inline u64	HvCallPci_eoi(u16	busNumberParm,
-				      u8	subBusParm,  
-				      u8	deviceIdParm)
+
+static inline u64 HvCallPci_eoi(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm)
 {
 	struct HvCallPci_DsaAddr dsa;
 	struct HvCallPci_LoadReturn retVal;
@@ -465,20 +391,13 @@
 
 	HvCall1Ret16(HvCallPciEoi, &retVal, *(u64*)&dsa);
 
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
 	return retVal.rc;
 }
-//============================================================================
-static inline u64	HvCallPci_getBarParms(u16	busNumberParm,
-					      u8	subBusParm,  
-					      u8	deviceIdParm,
-					      u8	barNumberParm,
-					      u64	parms,
-					      u32	sizeofParms)
+
+static inline u64 HvCallPci_getBarParms(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u8 barNumberParm, u64 parms, u32 sizeofParms)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
 	*((u64*)&dsa) = 0;
 
@@ -487,62 +406,13 @@
 	dsa.deviceId = deviceIdParm;
 	dsa.barNumber = barNumberParm;
 
-	retVal = HvCall3(HvCallPciGetBarParms, *(u64*)&dsa, parms, sizeofParms);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall3(HvCallPciGetBarParms, *(u64*)&dsa, parms, sizeofParms);
 }
-//============================================================================
-static inline u64	HvCallPci_maskFisr(u16	busNumberParm,
-					   u8	subBusParm,  
-					   u8	deviceIdParm,
-					   u64	fisrMask)
+
+static inline u64 HvCallPci_maskFisr(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u64 fisrMask)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
-
-	*((u64*)&dsa) = 0;		
-
-	dsa.busNumber = busNumberParm;
-	dsa.subBusNumber = subBusParm;
-	dsa.deviceId = deviceIdParm;
-
-	retVal = HvCall2(HvCallPciMaskFisr, *(u64*)&dsa, fisrMask);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
-}
-//============================================================================
-static inline u64	HvCallPci_unmaskFisr(u16	busNumberParm,
-					     u8		subBusParm,  
-					     u8		deviceIdParm,
-					     u64	fisrMask)
-{
-	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
-
-	*((u64*)&dsa) = 0;		
-
-	dsa.busNumber = busNumberParm;
-	dsa.subBusNumber = subBusParm;
-	dsa.deviceId = deviceIdParm;
-
-	retVal = HvCall2(HvCallPciUnmaskFisr, *(u64*)&dsa, fisrMask);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
-}
-//============================================================================
-static inline u64	HvCallPci_setSlotReset(u16		busNumberParm,
-					       u8		subBusParm,
-					       u8		deviceIdParm,
-					       u64		onNotOff)
-{
-	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
 	*((u64*)&dsa) = 0;
 
@@ -550,21 +420,41 @@
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 
-	retVal = HvCall2(HvCallPciSetSlotReset, *(u64*)&dsa, onNotOff);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall2(HvCallPciMaskFisr, *(u64*)&dsa, fisrMask);
 }
-//============================================================================
-static inline u64	HvCallPci_getDeviceInfo(u16	busNumberParm,
-						u8	subBusParm,  
-						u8	deviceNumberParm,
-						u64     parms,
-						u32	sizeofParms)
+
+static inline u64 HvCallPci_unmaskFisr(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u64 fisrMask)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
+
+	*((u64*)&dsa) = 0;
+
+	dsa.busNumber = busNumberParm;
+	dsa.subBusNumber = subBusParm;
+	dsa.deviceId = deviceIdParm;
+
+	return HvCall2(HvCallPciUnmaskFisr, *(u64*)&dsa, fisrMask);
+}
+
+static inline u64 HvCallPci_setSlotReset(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u64 onNotOff)
+{
+	struct HvCallPci_DsaAddr dsa;
+
+	*((u64*)&dsa) = 0;
+
+	dsa.busNumber = busNumberParm;
+	dsa.subBusNumber = subBusParm;
+	dsa.deviceId = deviceIdParm;
+
+	return HvCall2(HvCallPciSetSlotReset, *(u64*)&dsa, onNotOff);
+}
+
+static inline u64 HvCallPci_getDeviceInfo(u16 busNumberParm, u8 subBusParm,
+		u8 deviceNumberParm, u64 parms, u32 sizeofParms)
+{
+	struct HvCallPci_DsaAddr dsa;
 
 	*((u64*)&dsa) = 0;
 
@@ -572,102 +462,72 @@
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceNumberParm << 4;
 
-	retVal = HvCall3(HvCallPciGetDeviceInfo, *(u64*)&dsa, parms, sizeofParms);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall3(HvCallPciGetDeviceInfo, *(u64*)&dsa, parms, sizeofParms);
 }
-//============================================================================
-static inline u64	HvCallPci_maskInterrupts(u16	busNumberParm,
-						 u8	subBusParm,  
-						 u8	deviceIdParm,
-						 u64	interruptMask)
+
+static inline u64 HvCallPci_maskInterrupts(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u64 interruptMask)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
-	*((u64*)&dsa) = 0;		
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 
-	retVal = HvCall2(HvCallPciMaskInterrupts, *(u64*)&dsa, interruptMask);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall2(HvCallPciMaskInterrupts, *(u64*)&dsa, interruptMask);
 }
-//============================================================================
-static inline u64	HvCallPci_unmaskInterrupts(u16	busNumberParm,
-						 u8		subBusParm,  
-						 u8		deviceIdParm,
-						 u64		interruptMask)
+
+static inline u64 HvCallPci_unmaskInterrupts(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u64 interruptMask)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
-	*((u64*)&dsa) = 0;		
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 
-	retVal = HvCall2(HvCallPciUnmaskInterrupts, *(u64*)&dsa, interruptMask);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall2(HvCallPciUnmaskInterrupts, *(u64*)&dsa, interruptMask);
 }
-//============================================================================
 
-static inline u64	HvCallPci_getBusUnitInfo(u16		busNumberParm,
-						 u8		subBusParm,  
-						 u8		deviceIdParm,
-						 u64            parms,
-						 u32		sizeofParms)
+static inline u64 HvCallPci_getBusUnitInfo(u16 busNumberParm, u8 subBusParm,
+		u8 deviceIdParm, u64 parms, u32 sizeofParms)
 {
 	struct HvCallPci_DsaAddr dsa;
-	u64 retVal;
 
-	*((u64*)&dsa) = 0;		
+	*((u64*)&dsa) = 0;
 
 	dsa.busNumber = busNumberParm;
 	dsa.subBusNumber = subBusParm;
 	dsa.deviceId = deviceIdParm;
 
-	retVal = HvCall3(HvCallPciGetBusUnitInfo, *(u64*)&dsa, parms, sizeofParms);
-
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-
-	return retVal;
+	return HvCall3(HvCallPciGetBusUnitInfo, *(u64*)&dsa, parms,
+			sizeofParms);
 }
-//============================================================================
 
-static inline int HvCallPci_getBusVpd(u16 busNumParm, u64 destParm, u16 sizeParm)
+static inline int HvCallPci_getBusVpd(u16 busNumParm, u64 destParm,
+		u16 sizeParm)
 {
-	int xRetSize;
-	u64 xRc = HvCall4(HvCallPciGetCardVpd, busNumParm, destParm, sizeParm, HvCallPci_BusVpd);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	u64 xRc = HvCall4(HvCallPciGetCardVpd, busNumParm, destParm,
+			sizeParm, HvCallPci_BusVpd);
 	if (xRc == -1)
-		xRetSize = -1;
+		return -1;
 	else
-		xRetSize = xRc & 0xFFFF;
-	return xRetSize;
+		return xRc & 0xFFFF;
 }
-//============================================================================
 
-static inline int HvCallPci_getBusAdapterVpd(u16 busNumParm, u64 destParm, u16 sizeParm)
+static inline int HvCallPci_getBusAdapterVpd(u16 busNumParm, u64 destParm,
+		u16 sizeParm)
 {
-	int xRetSize;
-	u64 xRc = HvCall4(HvCallPciGetCardVpd, busNumParm, destParm, sizeParm, HvCallPci_BusAdapterVpd);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
+	u64 xRc = HvCall4(HvCallPciGetCardVpd, busNumParm, destParm,
+			sizeParm, HvCallPci_BusAdapterVpd);
 	if (xRc == -1)
-		xRetSize = -1;
+		return -1;
 	else
-		xRetSize = xRc & 0xFFFF;
-	return xRetSize;
+		return xRc & 0xFFFF;
 }
-//============================================================================
+
 #endif /* _HVCALLPCI_H */
diff --git a/include/asm-ppc64/iSeries/HvCallSc.h b/include/asm-ppc64/iSeries/HvCallSc.h
index eea2584..a62cef3 100644
--- a/include/asm-ppc64/iSeries/HvCallSc.h
+++ b/include/asm-ppc64/iSeries/HvCallSc.h
@@ -1,17 +1,17 @@
 /*
  * HvCallSc.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,7 +19,7 @@
 #ifndef _HVCALLSC_H
 #define _HVCALLSC_H
 
-#include <asm/iSeries/HvTypes.h>
+#include <linux/types.h>
 
 #define HvCallBase		0x8000000000000000ul
 #define HvCallCc		0x8001000000000000ul
@@ -30,22 +30,22 @@
 #define HvCallSm		0x8007000000000000ul
 #define HvCallXm		0x8009000000000000ul
 
-u64 HvCall0( u64 );
-u64 HvCall1( u64, u64 );
-u64 HvCall2( u64, u64, u64 );
-u64 HvCall3( u64, u64, u64, u64 );
-u64 HvCall4( u64, u64, u64, u64, u64 );
-u64 HvCall5( u64, u64, u64, u64, u64, u64 );
-u64 HvCall6( u64, u64, u64, u64, u64, u64, u64 );
-u64 HvCall7( u64, u64, u64, u64, u64, u64, u64, u64 );
+extern u64 HvCall0(u64);
+extern u64 HvCall1(u64, u64);
+extern u64 HvCall2(u64, u64, u64);
+extern u64 HvCall3(u64, u64, u64, u64);
+extern u64 HvCall4(u64, u64, u64, u64, u64);
+extern u64 HvCall5(u64, u64, u64, u64, u64, u64);
+extern u64 HvCall6(u64, u64, u64, u64, u64, u64, u64);
+extern u64 HvCall7(u64, u64, u64, u64, u64, u64, u64, u64);
 
-u64 HvCall0Ret16( u64, void * );
-u64 HvCall1Ret16( u64, void *, u64 );
-u64 HvCall2Ret16( u64, void *, u64, u64 );
-u64 HvCall3Ret16( u64, void *, u64, u64, u64 );
-u64 HvCall4Ret16( u64, void *, u64, u64, u64, u64 );
-u64 HvCall5Ret16( u64, void *, u64, u64, u64, u64, u64 );
-u64 HvCall6Ret16( u64, void *, u64, u64, u64, u64, u64, u64 );
-u64 HvCall7Ret16( u64, void *, u64, u64 ,u64 ,u64 ,u64 ,u64 ,u64 );
+extern u64 HvCall0Ret16(u64, void *);
+extern u64 HvCall1Ret16(u64, void *, u64);
+extern u64 HvCall2Ret16(u64, void *, u64, u64);
+extern u64 HvCall3Ret16(u64, void *, u64, u64, u64);
+extern u64 HvCall4Ret16(u64, void *, u64, u64, u64, u64);
+extern u64 HvCall5Ret16(u64, void *, u64, u64, u64, u64, u64);
+extern u64 HvCall6Ret16(u64, void *, u64, u64, u64, u64, u64, u64);
+extern u64 HvCall7Ret16(u64, void *, u64, u64 ,u64 ,u64 ,u64 ,u64 ,u64);
 
 #endif /* _HVCALLSC_H */
diff --git a/include/asm-ppc64/iSeries/HvCallSm.h b/include/asm-ppc64/iSeries/HvCallSm.h
index 9050c94..8a3dbb0 100644
--- a/include/asm-ppc64/iSeries/HvCallSm.h
+++ b/include/asm-ppc64/iSeries/HvCallSm.h
@@ -1,17 +1,17 @@
 /*
  * HvCallSm.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,34 +19,20 @@
 #ifndef _HVCALLSM_H
 #define _HVCALLSM_H
 
-//============================================================================
-//
-//	This file contains the "hypervisor call" interface which is used to
-//	drive the hypervisor from the OS.
-//
-//============================================================================
+/*
+ * This file contains the "hypervisor call" interface which is used to
+ * drive the hypervisor from the OS.
+ */
 
-//-------------------------------------------------------------------
-// Standard Includes
-//-------------------------------------------------------------------
 #include <asm/iSeries/HvCallSc.h>
 #include <asm/iSeries/HvTypes.h>
 
-//-----------------------------------------------------------------------------
-// Constants
-//-----------------------------------------------------------------------------
-
 #define HvCallSmGet64BitsOfAccessMap	HvCallSm  + 11
 
-
-//============================================================================
-static inline u64		HvCallSm_get64BitsOfAccessMap(
-					HvLpIndex lpIndex, u64 indexIntoBitMap )
+static inline u64 HvCallSm_get64BitsOfAccessMap(HvLpIndex lpIndex,
+		u64 indexIntoBitMap)
 {
-	u64 retval = HvCall2(HvCallSmGet64BitsOfAccessMap, lpIndex,
-			     indexIntoBitMap );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retval;
+	return HvCall2(HvCallSmGet64BitsOfAccessMap, lpIndex, indexIntoBitMap);
 }
-//============================================================================
+
 #endif /* _HVCALLSM_H */
diff --git a/include/asm-ppc64/iSeries/HvCallXm.h b/include/asm-ppc64/iSeries/HvCallXm.h
index bfb898f..8b9ba60 100644
--- a/include/asm-ppc64/iSeries/HvCallXm.h
+++ b/include/asm-ppc64/iSeries/HvCallXm.h
@@ -1,30 +1,13 @@
-//============================================================================
-//							 Header File Id
-// Name______________:	HvCallXm.H
-//
-// Description_______:
-//
-//	This file contains the "hypervisor call" interface which is used to
-//	drive the hypervisor from SLIC.
-//
-//============================================================================
+/*
+ * This file contains the "hypervisor call" interface which is used to
+ * drive the hypervisor from SLIC.
+ */
 #ifndef _HVCALLXM_H
 #define _HVCALLXM_H
 
-//-------------------------------------------------------------------
-// Forward declarations 
-//-------------------------------------------------------------------
-
-//-------------------------------------------------------------------
-// Standard Includes
-//-------------------------------------------------------------------
 #include <asm/iSeries/HvCallSc.h>
 #include <asm/iSeries/HvTypes.h>
 
-//-----------------------------------------------------------------------------
-// Constants
-//-----------------------------------------------------------------------------
-
 #define HvCallXmGetTceTableParms	HvCallXm +  0
 #define HvCallXmTestBus			HvCallXm +  1
 #define HvCallXmConnectBusUnit		HvCallXm +  2
@@ -33,63 +16,63 @@
 #define HvCallXmSetTce			HvCallXm + 11
 #define HvCallXmSetTces			HvCallXm + 13
 
+/*
+ * Structure passed to HvCallXm_getTceTableParms
+ */
+struct iommu_table_cb {
+	unsigned long	itc_busno;	/* Bus number for this tce table */
+	unsigned long	itc_start;	/* Will be NULL for secondary */
+	unsigned long	itc_totalsize;	/* Size (in pages) of whole table */
+	unsigned long	itc_offset;	/* Index into real tce table of the
+					   start of our section */
+	unsigned long	itc_size;	/* Size (in pages) of our section */
+	unsigned long	itc_index;	/* Index of this tce table */
+	unsigned short	itc_maxtables;	/* Max num of tables for partition */
+	unsigned char	itc_virtbus;	/* Flag to indicate virtual bus */
+	unsigned char	itc_slotno;	/* IOA Tce Slot Index */
+	unsigned char	itc_rsvd[4];
+};
 
-
-//============================================================================
-static inline void		HvCallXm_getTceTableParms(u64 cb)
+static inline void HvCallXm_getTceTableParms(u64 cb)
 {
 	HvCall1(HvCallXmGetTceTableParms, cb);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
 }
-//============================================================================
-static inline u64		HvCallXm_setTce(u64 tceTableToken, u64 tceOffset, u64 tce)
-{	
-	u64 retval = HvCall3(HvCallXmSetTce, tceTableToken, tceOffset, tce );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retval;
-}
-//============================================================================
-static inline u64		HvCallXm_setTces(u64 tceTableToken, u64 tceOffset, u64 numTces, u64 tce1, u64 tce2, u64 tce3, u64 tce4)
-{	
-	u64 retval = HvCall7(HvCallXmSetTces, tceTableToken, tceOffset, numTces,
-			     tce1, tce2, tce3, tce4 );
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retval;
-}
-//=============================================================================
-static inline u64	HvCallXm_testBus(u16 busNumber)
-{
-	u64 retVal = HvCall1(HvCallXmTestBus, busNumber);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//=====================================================================================
-static inline u64	HvCallXm_testBusUnit(u16 busNumber, u8 subBusNumber, u8 deviceId)
-{
-	u64 busUnitNumber = (subBusNumber << 8) | deviceId;
-	u64 retVal = HvCall2(HvCallXmTestBusUnit, busNumber, busUnitNumber);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//=====================================================================================
-static inline u64	HvCallXm_connectBusUnit(u16 busNumber, u8 subBusNumber, u8 deviceId,
-						u64 interruptToken)
-{
-	u64 busUnitNumber = (subBusNumber << 8) | deviceId;
-	u64 queueIndex = 0; // HvLpConfig::mapDsaToQueueIndex(HvLpDSA(busNumber, xBoard, xCard));  
 
-	u64 retVal = HvCall5(HvCallXmConnectBusUnit, busNumber, busUnitNumber,
-			     interruptToken, 0, queueIndex);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
-}
-//=====================================================================================
-static inline u64	HvCallXm_loadTod(void)
+static inline u64 HvCallXm_setTce(u64 tceTableToken, u64 tceOffset, u64 tce)
 {
-	u64 retVal = HvCall0(HvCallXmLoadTod);
-	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
-	return retVal;
+	return HvCall3(HvCallXmSetTce, tceTableToken, tceOffset, tce);
 }
-//=====================================================================================
+
+static inline u64 HvCallXm_setTces(u64 tceTableToken, u64 tceOffset,
+		u64 numTces, u64 tce1, u64 tce2, u64 tce3, u64 tce4)
+{
+	return HvCall7(HvCallXmSetTces, tceTableToken, tceOffset, numTces,
+			     tce1, tce2, tce3, tce4);
+}
+
+static inline u64 HvCallXm_testBus(u16 busNumber)
+{
+	return HvCall1(HvCallXmTestBus, busNumber);
+}
+
+static inline u64 HvCallXm_testBusUnit(u16 busNumber, u8 subBusNumber,
+		u8 deviceId)
+{
+	return HvCall2(HvCallXmTestBusUnit, busNumber,
+			(subBusNumber << 8) | deviceId);
+}
+
+static inline u64 HvCallXm_connectBusUnit(u16 busNumber, u8 subBusNumber,
+		u8 deviceId, u64 interruptToken)
+{
+	return HvCall5(HvCallXmConnectBusUnit, busNumber,
+			(subBusNumber << 8) | deviceId, interruptToken, 0,
+			0 /* HvLpConfig::mapDsaToQueueIndex(HvLpDSA(busNumber, xBoard, xCard)) */);
+}
+
+static inline u64 HvCallXm_loadTod(void)
+{
+	return HvCall0(HvCallXmLoadTod);
+}
 
 #endif /* _HVCALLXM_H */
diff --git a/include/asm-ppc64/iSeries/HvLpConfig.h b/include/asm-ppc64/iSeries/HvLpConfig.h
index bdbd70f..f1cf1e7 100644
--- a/include/asm-ppc64/iSeries/HvLpConfig.h
+++ b/include/asm-ppc64/iSeries/HvLpConfig.h
@@ -1,17 +1,17 @@
 /*
  * HvLpConfig.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,262 +19,120 @@
 #ifndef _HVLPCONFIG_H
 #define _HVLPCONFIG_H
 
-//===========================================================================
-//
-//      This file contains the interface to the LPAR configuration data
-//  to determine which resources should be allocated to each partition.
-//
-//===========================================================================
+/*
+ * This file contains the interface to the LPAR configuration data
+ * to determine which resources should be allocated to each partition.
+ */
 
-#include <asm/iSeries/HvCallCfg.h>
+#include <asm/iSeries/HvCallSc.h>
 #include <asm/iSeries/HvTypes.h>
 #include <asm/iSeries/ItLpNaca.h>
-#include <asm/iSeries/LparData.h>
 
-//-------------------------------------------------------------------
-// Constants
-//-------------------------------------------------------------------
+enum {
+	HvCallCfg_Cur	= 0,
+	HvCallCfg_Init	= 1,
+	HvCallCfg_Max	= 2,
+	HvCallCfg_Min	= 3
+};
+
+#define HvCallCfgGetSystemPhysicalProcessors		HvCallCfg +  6
+#define HvCallCfgGetPhysicalProcessors			HvCallCfg +  7
+#define HvCallCfgGetMsChunks				HvCallCfg +  9
+#define HvCallCfgGetSharedPoolIndex			HvCallCfg + 20
+#define HvCallCfgGetSharedProcUnits			HvCallCfg + 21
+#define HvCallCfgGetNumProcsInSharedPool		HvCallCfg + 22
+#define HvCallCfgGetVirtualLanIndexMap			HvCallCfg + 30
+#define HvCallCfgGetHostingLpIndex			HvCallCfg + 32
 
 extern HvLpIndex HvLpConfig_getLpIndex_outline(void);
 
-//===================================================================
 static inline HvLpIndex	HvLpConfig_getLpIndex(void)
 {
 	return itLpNaca.xLpIndex;
 }
-//===================================================================
+
 static inline HvLpIndex	HvLpConfig_getPrimaryLpIndex(void)
 {
 	return itLpNaca.xPrimaryLpIndex;
 }
-//=================================================================
-static inline HvLpIndex	HvLpConfig_getLps(void)
+
+static inline u64 HvLpConfig_getMsChunks(void)
 {
-	return HvCallCfg_getLps();
+	return HvCall2(HvCallCfgGetMsChunks, HvLpConfig_getLpIndex(),
+			HvCallCfg_Cur);
 }
-//=================================================================
-static inline HvLpIndexMap	HvLpConfig_getActiveLpMap(void)
+
+static inline u64 HvLpConfig_getSystemPhysicalProcessors(void)
 {
-	return HvCallCfg_getActiveLpMap();
+	return HvCall0(HvCallCfgGetSystemPhysicalProcessors);
 }
-//=================================================================
-static inline u64		HvLpConfig_getSystemMsMegs(void)
+
+static inline u64 HvLpConfig_getNumProcsInSharedPool(HvLpSharedPoolIndex sPI)
 {
-	return HvCallCfg_getSystemMsChunks() / HVCHUNKSPERMEG;
+	return (u16)HvCall1(HvCallCfgGetNumProcsInSharedPool, sPI);
 }
-//=================================================================
-static inline u64		HvLpConfig_getSystemMsChunks(void)
+
+static inline u64 HvLpConfig_getPhysicalProcessors(void)
 {
-	return HvCallCfg_getSystemMsChunks();
+	return HvCall2(HvCallCfgGetPhysicalProcessors, HvLpConfig_getLpIndex(),
+			HvCallCfg_Cur);
 }
-//=================================================================
-static inline u64		HvLpConfig_getSystemMsPages(void)
+
+static inline HvLpSharedPoolIndex HvLpConfig_getSharedPoolIndex(void)
 {
-	return HvCallCfg_getSystemMsChunks() * HVPAGESPERCHUNK;
+	return HvCall1(HvCallCfgGetSharedPoolIndex, HvLpConfig_getLpIndex());
 }
-//================================================================
-static inline u64		HvLpConfig_getMsMegs(void)
+
+static inline u64 HvLpConfig_getSharedProcUnits(void)
 {
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Cur) / HVCHUNKSPERMEG;
+	return HvCall2(HvCallCfgGetSharedProcUnits, HvLpConfig_getLpIndex(),
+			HvCallCfg_Cur);
 }
-//================================================================
-static inline u64		HvLpConfig_getMsChunks(void)
+
+static inline u64 HvLpConfig_getMaxSharedProcUnits(void)
 {
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Cur);
+	return HvCall2(HvCallCfgGetSharedProcUnits, HvLpConfig_getLpIndex(),
+			HvCallCfg_Max);
 }
-//================================================================
-static inline u64		HvLpConfig_getMsPages(void)
+
+static inline u64 HvLpConfig_getMaxPhysicalProcessors(void)
 {
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Cur) * HVPAGESPERCHUNK;
+	return HvCall2(HvCallCfgGetPhysicalProcessors, HvLpConfig_getLpIndex(),
+			HvCallCfg_Max);
 }
-//================================================================
-static inline u64		HvLpConfig_getMinMsMegs(void)
+
+static inline HvLpVirtualLanIndexMap HvLpConfig_getVirtualLanIndexMapForLp(
+		HvLpIndex lp)
 {
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Min) / HVCHUNKSPERMEG;
+	/*
+	 * This is a new function in V5R1 so calls to this on older
+	 * hypervisors will return -1
+	 */
+	u64 retVal = HvCall1(HvCallCfgGetVirtualLanIndexMap, lp);
+	if (retVal == -1)
+		retVal = 0;
+	return retVal;
 }
-//================================================================
-static inline u64		HvLpConfig_getMinMsChunks(void)
+
+static inline HvLpVirtualLanIndexMap HvLpConfig_getVirtualLanIndexMap(void)
 {
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Min);
+	return HvLpConfig_getVirtualLanIndexMapForLp(
+			HvLpConfig_getLpIndex_outline());
 }
-//================================================================
-static inline u64		HvLpConfig_getMinMsPages(void)
+
+static inline int HvLpConfig_doLpsCommunicateOnVirtualLan(HvLpIndex lp1,
+		HvLpIndex lp2)
 {
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Min) * HVPAGESPERCHUNK;
-}
-//================================================================
-static inline u64		HvLpConfig_getMinRuntimeMsMegs(void)
-{
-	return HvCallCfg_getMinRuntimeMsChunks(HvLpConfig_getLpIndex()) / HVCHUNKSPERMEG;
-}
-//===============================================================
-static inline u64		HvLpConfig_getMinRuntimeMsChunks(void)
-{
-	return HvCallCfg_getMinRuntimeMsChunks(HvLpConfig_getLpIndex());
-}
-//===============================================================
-static inline u64		HvLpConfig_getMinRuntimeMsPages(void)
-{
-	return HvCallCfg_getMinRuntimeMsChunks(HvLpConfig_getLpIndex()) * HVPAGESPERCHUNK;
-}
-//===============================================================
-static inline u64		HvLpConfig_getMaxMsMegs(void)
-{
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Max) / HVCHUNKSPERMEG;
-}
-//===============================================================
-static inline u64		HvLpConfig_getMaxMsChunks(void)
-{
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Max);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMaxMsPages(void)
-{
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Max) * HVPAGESPERCHUNK;
-}
-//===============================================================
-static inline u64		HvLpConfig_getInitMsMegs(void)
-{
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Init) / HVCHUNKSPERMEG;
-}
-//===============================================================
-static inline u64		HvLpConfig_getInitMsChunks(void)
-{
-	return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Init);
-}
-//===============================================================
-static inline u64		HvLpConfig_getInitMsPages(void)
-{    return HvCallCfg_getMsChunks(HvLpConfig_getLpIndex(),HvCallCfg_Init) * HVPAGESPERCHUNK;
-}
-//===============================================================
-static inline u64		HvLpConfig_getSystemPhysicalProcessors(void)
-{
-	return HvCallCfg_getSystemPhysicalProcessors();
-}
-//===============================================================
-static inline u64		HvLpConfig_getSystemLogicalProcessors(void)
-{
-	return HvCallCfg_getSystemPhysicalProcessors() * (/*getPaca()->getSecondaryThreadCount() +*/ 1);
-}
-//===============================================================
-static inline u64		HvLpConfig_getNumProcsInSharedPool(HvLpSharedPoolIndex sPI)
-{
-	return HvCallCfg_getNumProcsInSharedPool(sPI);
-}
-//===============================================================
-static inline u64		HvLpConfig_getPhysicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Cur);
-}
-//===============================================================
-static inline u64		HvLpConfig_getLogicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Cur) * (/*getPaca()->getSecondaryThreadCount() +*/ 1);
-}
-//===============================================================
-static inline HvLpSharedPoolIndex	HvLpConfig_getSharedPoolIndex(void)
-{
-	return HvCallCfg_getSharedPoolIndex(HvLpConfig_getLpIndex());
-}
-//===============================================================
-static inline u64		HvLpConfig_getSharedProcUnits(void)
-{
-	return HvCallCfg_getSharedProcUnits(HvLpConfig_getLpIndex(),HvCallCfg_Cur);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMinSharedProcUnits(void)
-{
-	return HvCallCfg_getSharedProcUnits(HvLpConfig_getLpIndex(),HvCallCfg_Min);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMaxSharedProcUnits(void)
-{
-	return HvCallCfg_getSharedProcUnits(HvLpConfig_getLpIndex(),HvCallCfg_Max);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMinPhysicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Min);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMinLogicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Min) * (/*getPaca()->getSecondaryThreadCount() +*/ 1);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMaxPhysicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Max);
-}
-//===============================================================
-static inline u64		HvLpConfig_getMaxLogicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Max) * (/*getPaca()->getSecondaryThreadCount() +*/ 1);
-}
-//===============================================================
-static inline u64		HvLpConfig_getInitPhysicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Init);
-}
-//===============================================================
-static inline u64		HvLpConfig_getInitLogicalProcessors(void)
-{
-	return HvCallCfg_getPhysicalProcessors(HvLpConfig_getLpIndex(),HvCallCfg_Init) * (/*getPaca()->getSecondaryThreadCount() +*/ 1);
-}
-//================================================================
-static inline HvLpVirtualLanIndexMap	HvLpConfig_getVirtualLanIndexMap(void)
-{
-	return HvCallCfg_getVirtualLanIndexMap(HvLpConfig_getLpIndex_outline());
-}
-//===============================================================
-static inline HvLpVirtualLanIndexMap	HvLpConfig_getVirtualLanIndexMapForLp(HvLpIndex lp)
-{
-	return HvCallCfg_getVirtualLanIndexMap(lp);
-}
-//================================================================
-static inline HvLpIndex	HvLpConfig_getBusOwner(HvBusNumber busNumber)
-{
-	return HvCallCfg_getBusOwner(busNumber);
-}
-//===============================================================
-static inline int		HvLpConfig_isBusDedicated(HvBusNumber busNumber)
-{
-	return HvCallCfg_isBusDedicated(busNumber);
-}
-//================================================================
-static inline HvLpIndexMap	HvLpConfig_getBusAllocation(HvBusNumber busNumber)
-{
-	return HvCallCfg_getBusAllocation(busNumber);
-}
-//================================================================
-// returns the absolute real address of the load area
-static inline u64		HvLpConfig_getLoadAddress(void)
-{
-	return itLpNaca.xLoadAreaAddr & 0x7fffffffffffffff;
-}
-//================================================================
-static inline u64		HvLpConfig_getLoadPages(void)
-{
-	return itLpNaca.xLoadAreaChunks * HVPAGESPERCHUNK;
-}
-//================================================================
-static inline int		HvLpConfig_isBusOwnedByThisLp(HvBusNumber busNumber)
-{
-	HvLpIndex busOwner = HvLpConfig_getBusOwner(busNumber);
-	return (busOwner == HvLpConfig_getLpIndex());
-}
-//================================================================
-static inline int         HvLpConfig_doLpsCommunicateOnVirtualLan(HvLpIndex lp1, HvLpIndex lp2)
-{
-	HvLpVirtualLanIndexMap virtualLanIndexMap1 = HvCallCfg_getVirtualLanIndexMap( lp1 );
-	HvLpVirtualLanIndexMap virtualLanIndexMap2 = HvCallCfg_getVirtualLanIndexMap( lp2 );
+	HvLpVirtualLanIndexMap virtualLanIndexMap1 =
+		HvLpConfig_getVirtualLanIndexMapForLp(lp1);
+	HvLpVirtualLanIndexMap virtualLanIndexMap2 =
+		HvLpConfig_getVirtualLanIndexMapForLp(lp2);
 	return ((virtualLanIndexMap1 & virtualLanIndexMap2) != 0);
 }
-//================================================================
-static inline HvLpIndex		HvLpConfig_getHostingLpIndex(HvLpIndex lp)
+
+static inline HvLpIndex HvLpConfig_getHostingLpIndex(HvLpIndex lp)
 {
-	return HvCallCfg_getHostingLpIndex(lp);
+	return HvCall1(HvCallCfgGetHostingLpIndex, lp);
 }
-//================================================================
 
 #endif /* _HVLPCONFIG_H */
diff --git a/include/asm-ppc64/iSeries/HvLpEvent.h b/include/asm-ppc64/iSeries/HvLpEvent.h
index 30936e43..865000d 100644
--- a/include/asm-ppc64/iSeries/HvLpEvent.h
+++ b/include/asm-ppc64/iSeries/HvLpEvent.h
@@ -1,27 +1,24 @@
 /*
  * HvLpEvent.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  */
 
-//======================================================================
-//
-//	This file contains the class for HV events in the system.
-//
-//=====================================================================
+/* This file contains the class for HV events in the system. */
+
 #ifndef _HVLPEVENT_H
 #define _HVLPEVENT_H
 
@@ -30,69 +27,70 @@
 #include <asm/iSeries/HvTypes.h>
 #include <asm/iSeries/HvCallEvent.h>
 
-//=====================================================================
-//
-// HvLpEvent is the structure for Lp Event messages passed between
-// partitions through PLIC. 
-//
-//=====================================================================
+/*
+ * HvLpEvent is the structure for Lp Event messages passed between
+ * partitions through PLIC.
+ */
 
-struct HvEventFlags
-{
-	u8	xValid:1;		// Indicates a valid request	x00-x00
-	u8	xRsvd1:4;		// Reserved			...
-	u8	xAckType:1;		// Immediate or deferred	...
-	u8	xAckInd:1;		// Indicates if ACK required	...
-	u8	xFunction:1;		// Interrupt or Acknowledge	...
+struct HvEventFlags {
+	u8	xValid:1;	/* Indicates a valid request	x00-x00 */
+	u8	xRsvd1:4;	/* Reserved			... */
+	u8	xAckType:1;	/* Immediate or deferred	... */
+	u8	xAckInd:1;	/* Indicates if ACK required	... */
+	u8	xFunction:1;	/* Interrupt or Acknowledge	... */
 };
 
 
-struct HvLpEvent
-{
-	struct HvEventFlags xFlags;	// Event flags			x00-x00
-	u8	xType;			// Type of message		x01-x01
-	u16	xSubtype;		// Subtype for event		x02-x03
-	u8	xSourceLp;		// Source LP			x04-x04
-	u8	xTargetLp;		// Target LP			x05-x05
-	u8	xSizeMinus1;		// Size of Derived class - 1	x06-x06
-	u8	xRc;			// RC for Ack flows		x07-x07
-	u16	xSourceInstanceId;	// Source sides instance id	x08-x09
-	u16	xTargetInstanceId;	// Target sides instance id	x0A-x0B
+struct HvLpEvent {
+	struct HvEventFlags xFlags;	/* Event flags		      x00-x00 */
+	u8	xType;			/* Type of message	      x01-x01 */
+	u16	xSubtype;		/* Subtype for event	      x02-x03 */
+	u8	xSourceLp;		/* Source LP		      x04-x04 */
+	u8	xTargetLp;		/* Target LP		      x05-x05 */
+	u8	xSizeMinus1;		/* Size of Derived class - 1  x06-x06 */
+	u8	xRc;			/* RC for Ack flows	      x07-x07 */
+	u16	xSourceInstanceId;	/* Source sides instance id   x08-x09 */
+	u16	xTargetInstanceId;	/* Target sides instance id   x0A-x0B */
 	union {
-		u32	xSubtypeData;	// Data usable by the subtype	x0C-x0F
-		u16	xSubtypeDataShort[2];	// Data as 2 shorts
-		u8	xSubtypeDataChar[4];	// Data as 4 chars
+		u32	xSubtypeData;	/* Data usable by the subtype x0C-x0F */
+		u16	xSubtypeDataShort[2];	/* Data as 2 shorts */
+		u8	xSubtypeDataChar[4];	/* Data as 4 chars */
 	} x;
 
-	u64	xCorrelationToken;	// Unique value for source/type x10-x17
+	u64	xCorrelationToken;	/* Unique value for source/type x10-x17 */
 };
 
-// Lp Event handler function
 typedef void (*LpEventHandler)(struct HvLpEvent *, struct pt_regs *);
 
-// Register a handler for an event type
-//  returns 0 on success
-extern int HvLpEvent_registerHandler( HvLpEvent_Type eventType, LpEventHandler hdlr);
+/* Register a handler for an event type - returns 0 on success */
+extern int HvLpEvent_registerHandler(HvLpEvent_Type eventType,
+		LpEventHandler hdlr);
 
-// Unregister a handler for an event type
-//  This call will sleep until the handler being removed is guaranteed to
-//  be no longer executing on any CPU. Do not call with locks held.
-//
-//  returns 0 on success
-//  Unregister will fail if there are any paths open for the type
-extern int HvLpEvent_unregisterHandler( HvLpEvent_Type eventType );
+/*
+ * Unregister a handler for an event type
+ *
+ * This call will sleep until the handler being removed is guaranteed to
+ * be no longer executing on any CPU. Do not call with locks held.
+ *
+ *  returns 0 on success
+ *  Unregister will fail if there are any paths open for the type
+ */
+extern int HvLpEvent_unregisterHandler(HvLpEvent_Type eventType);
 
-// Open an Lp Event Path for an event type
-//  returns 0 on success
-//  openPath will fail if there is no handler registered for the event type.
-//  The lpIndex specified is the partition index for the target partition
-//  (for VirtualIo, VirtualLan and SessionMgr) other types specify zero) 
-extern int HvLpEvent_openPath( HvLpEvent_Type eventType, HvLpIndex lpIndex );
+/*
+ * Open an Lp Event Path for an event type
+ * returns 0 on success
+ * openPath will fail if there is no handler registered for the event type.
+ * The lpIndex specified is the partition index for the target partition
+ * (for VirtualIo, VirtualLan and SessionMgr) other types specify zero)
+ */
+extern int HvLpEvent_openPath(HvLpEvent_Type eventType, HvLpIndex lpIndex);
 
-
-// Close an Lp Event Path for a type and partition
-//  returns 0 on sucess
-extern int HvLpEvent_closePath( HvLpEvent_Type eventType, HvLpIndex lpIndex );
+/*
+ * Close an Lp Event Path for a type and partition
+ * returns 0 on sucess
+ */
+extern int HvLpEvent_closePath(HvLpEvent_Type eventType, HvLpIndex lpIndex);
 
 #define HvLpEvent_Type_Hypervisor 0
 #define HvLpEvent_Type_MachineFac 1
@@ -141,4 +139,4 @@
 #define HvLpDma_Rc_InvalidAddress 4
 #define HvLpDma_Rc_InvalidLength 5
 
-#endif // _HVLPEVENT_H
+#endif /* _HVLPEVENT_H */
diff --git a/include/asm-ppc64/iSeries/HvReleaseData.h b/include/asm-ppc64/iSeries/HvReleaseData.h
index 183e5e7..01a1f13 100644
--- a/include/asm-ppc64/iSeries/HvReleaseData.h
+++ b/include/asm-ppc64/iSeries/HvReleaseData.h
@@ -1,17 +1,17 @@
 /*
  * HvReleaseData.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,47 +19,45 @@
 #ifndef _HVRELEASEDATA_H
 #define _HVRELEASEDATA_H
 
-//=============================================================================
-//
-//   This control block contains the critical information about the 
-//   release so that it can be changed in the future (ie, the virtual 
-//   address of the OS's NACA).
-//
+/*
+ * This control block contains the critical information about the
+ * release so that it can be changed in the future (ie, the virtual
+ * address of the OS's NACA).
+ */
 #include <asm/types.h>
 #include <asm/naca.h>
 
-//=============================================================================
-//
-//	When we IPL a secondary partition, we will check if if the 
-//	secondary xMinPlicVrmIndex > the primary xVrmIndex.  
-//	If it is then this tells PLIC that this secondary is not 
-//	supported running on this "old" of a level of PLIC.
-//
-//	Likewise, we will compare the primary xMinSlicVrmIndex to 
-//	the secondary xVrmIndex. 
-//	If the primary xMinSlicVrmDelta > secondary xVrmDelta then we 
-//	know that this PLIC does not support running an OS "that old".
-//
-//=============================================================================
+/*
+ * When we IPL a secondary partition, we will check if if the
+ * secondary xMinPlicVrmIndex > the primary xVrmIndex.
+ * If it is then this tells PLIC that this secondary is not
+ * supported running on this "old" of a level of PLIC.
+ *
+ * Likewise, we will compare the primary xMinSlicVrmIndex to
+ * the secondary xVrmIndex.
+ * If the primary xMinSlicVrmDelta > secondary xVrmDelta then we
+ * know that this PLIC does not support running an OS "that old".
+ */
 
-struct	HvReleaseData
-{
-	u32	xDesc;			// Descriptor	"HvRD" ebcdic	x00-x03
-	u16	xSize;			// Size of this control block	x04-x05
-	u16	xVpdAreasPtrOffset;	// Offset in NACA of ItVpdAreas	x06-x07
-	struct  naca_struct * xSlicNacaAddr; // Virt addr of SLIC NACA  x08-x0F
-	u32	xMsNucDataOffset;	// Offset of Linux Mapping Data x10-x13
-	u32	xRsvd1;			// Reserved			x14-x17
-	u16	xTagsMode:1;		// 0 == tags active, 1 == tags inactive
-	u16	xAddressSize:1;		// 0 == 64-bit, 1 == 32-bit
-	u16	xNoSharedProcs:1;	// 0 == shared procs, 1 == no shared
-	u16	xNoHMT:1;		// 0 == allow HMT, 1 == no HMT
-	u16	xRsvd2:12;		// Reserved			x18-x19
-	u16	xVrmIndex;		// VRM Index of OS image	x1A-x1B
-	u16	xMinSupportedPlicVrmIndex;// Min PLIC level  (soft)	x1C-x1D
-	u16	xMinCompatablePlicVrmIndex;// Min PLIC levelP (hard)	x1E-x1F
-	char	xVrmName[12];		// Displayable name  		x20-x2B
-	char	xRsvd3[20];		// Reserved			x2C-x3F
+struct HvReleaseData {
+	u32	xDesc;		/* Descriptor "HvRD" ebcdic	x00-x03 */
+	u16	xSize;		/* Size of this control block	x04-x05 */
+	u16	xVpdAreasPtrOffset; /* Offset in NACA of ItVpdAreas x06-x07 */
+	struct  naca_struct	*xSlicNacaAddr; /* Virt addr of SLIC NACA x08-x0F */
+	u32	xMsNucDataOffset; /* Offset of Linux Mapping Data x10-x13 */
+	u32	xRsvd1;		/* Reserved			x14-x17 */
+	u16	xTagsMode:1;	/* 0 == tags active, 1 == tags inactive */
+	u16	xAddressSize:1;	/* 0 == 64-bit, 1 == 32-bit */
+	u16	xNoSharedProcs:1; /* 0 == shared procs, 1 == no shared */
+	u16	xNoHMT:1;	/* 0 == allow HMT, 1 == no HMT */
+	u16	xRsvd2:12;	/* Reserved			x18-x19 */
+	u16	xVrmIndex;	/* VRM Index of OS image	x1A-x1B */
+	u16	xMinSupportedPlicVrmIndex; /* Min PLIC level  (soft) x1C-x1D */
+	u16	xMinCompatablePlicVrmIndex; /* Min PLIC levelP (hard) x1E-x1F */
+	char	xVrmName[12];	/* Displayable name		x20-x2B */
+	char	xRsvd3[20];	/* Reserved			x2C-x3F */
 };
 
+extern struct HvReleaseData	hvReleaseData;
+
 #endif /* _HVRELEASEDATA_H */
diff --git a/include/asm-ppc64/iSeries/HvTypes.h b/include/asm-ppc64/iSeries/HvTypes.h
index 3ec49c1..b1ef2b4 100644
--- a/include/asm-ppc64/iSeries/HvTypes.h
+++ b/include/asm-ppc64/iSeries/HvTypes.h
@@ -1,17 +1,17 @@
 /*
  * HvTypes.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,74 +19,60 @@
 #ifndef _HVTYPES_H
 #define _HVTYPES_H
 
-//===========================================================================
-//                                                             Header File Id
-// Name______________:  HvTypes.H
-//
-// Description_______:
-//
-//	General typedefs for the hypervisor.
-//
-// Declared Class(es):
-//
-//===========================================================================
+/*
+ * General typedefs for the hypervisor.
+ */
 
 #include <asm/types.h>
 
-//-------------------------------------------------------------------
-// Typedefs
-//-------------------------------------------------------------------
 typedef u8	HvLpIndex;
 typedef u16	HvLpInstanceId;
-typedef u64     HvLpTOD;
-typedef u64     HvLpSystemSerialNum;
-typedef u8      HvLpDeviceSerialNum[12];
-typedef u16     HvLpSanHwSet;
-typedef u16     HvLpBus;
-typedef u16     HvLpBoard;
-typedef u16     HvLpCard;
-typedef u8      HvLpDeviceType[4];
-typedef u8      HvLpDeviceModel[3];
-typedef u64     HvIoToken;
-typedef u8      HvLpName[8];
+typedef u64	HvLpTOD;
+typedef u64	HvLpSystemSerialNum;
+typedef u8	HvLpDeviceSerialNum[12];
+typedef u16	HvLpSanHwSet;
+typedef u16	HvLpBus;
+typedef u16	HvLpBoard;
+typedef u16	HvLpCard;
+typedef u8	HvLpDeviceType[4];
+typedef u8	HvLpDeviceModel[3];
+typedef u64	HvIoToken;
+typedef u8	HvLpName[8];
 typedef u32	HvIoId;
 typedef u64	HvRealMemoryIndex;
-typedef u32     HvLpIndexMap;		// Must hold HvMaxArchitectedLps bits!!!
+typedef u32	HvLpIndexMap;	/* Must hold HVMAXARCHITECTEDLPS bits!!! */
 typedef u16	HvLpVrmIndex;
 typedef u32	HvXmGenerationId;
-typedef u8	HvLpBusPool;			
-typedef u8	HvLpSharedPoolIndex;		
+typedef u8	HvLpBusPool;
+typedef u8	HvLpSharedPoolIndex;
 typedef u16	HvLpSharedProcUnitsX100;
 typedef u8	HvLpVirtualLanIndex;
-typedef u16	HvLpVirtualLanIndexMap;	// Must hold HvMaxArchitectedVirtualLans bits!!!
-typedef u16	HvBusNumber;		// Hypervisor Bus Number
-typedef u8	HvSubBusNumber;		// Hypervisor SubBus Number
-typedef u8	HvAgentId;		// Hypervisor DevFn
+typedef u16	HvLpVirtualLanIndexMap;	/* Must hold HVMAXARCHITECTEDVIRTUALLANS bits!!! */
+typedef u16	HvBusNumber;	/* Hypervisor Bus Number */
+typedef u8	HvSubBusNumber;	/* Hypervisor SubBus Number */
+typedef u8	HvAgentId;	/* Hypervisor DevFn */
 
 
-#define HVMAXARCHITECTEDLPS 32
-#define HVMAXARCHITECTEDVIRTUALLANS 16
-#define HVMAXARCHITECTEDVIRTUALDISKS 32
-#define HVMAXARCHITECTEDVIRTUALCDROMS 8
-#define HVMAXARCHITECTEDVIRTUALTAPES 8
-#define HVCHUNKSIZE 256 * 1024
-#define HVPAGESIZE 4 * 1024
-#define HVLPMINMEGSPRIMARY 256
-#define HVLPMINMEGSSECONDARY 64
-#define HVCHUNKSPERMEG 4
-#define HVPAGESPERMEG 256
-#define HVPAGESPERCHUNK 64
- 
-#define HvMaxArchitectedLps 		((HvLpIndex)HVMAXARCHITECTEDLPS)
-#define HvMaxArchitectedVirtualLans	((HvLpVirtualLanIndex)16)
+#define HVMAXARCHITECTEDLPS		32
+#define HVMAXARCHITECTEDVIRTUALLANS	16
+#define HVMAXARCHITECTEDVIRTUALDISKS	32
+#define HVMAXARCHITECTEDVIRTUALCDROMS	8
+#define HVMAXARCHITECTEDVIRTUALTAPES	8
+#define HVCHUNKSIZE			(256 * 1024)
+#define HVPAGESIZE			(4 * 1024)
+#define HVLPMINMEGSPRIMARY		256
+#define HVLPMINMEGSSECONDARY		64
+#define HVCHUNKSPERMEG			4
+#define HVPAGESPERMEG			256
+#define HVPAGESPERCHUNK			64
+
 #define HvLpIndexInvalid		((HvLpIndex)0xff)
 
-//--------------------------------------------------------------------
-// Enums for the sub-components under PLIC
-// Used in HvCall  and HvPrimaryCall
-//--------------------------------------------------------------------
-enum   HvCallCompIds
-{
+/*
+ * Enums for the sub-components under PLIC
+ * Used in HvCall  and HvPrimaryCall
+ */
+enum {
 	HvCallCompId = 0,
 	HvCallCpuCtlsCompId = 1,
 	HvCallCfgCompId = 2,
@@ -97,18 +83,18 @@
 	HvCallSmCompId = 7,
 	HvCallSpdCompId = 8,
 	HvCallXmCompId = 9,
-	HvCallRioCompId = 10, 
+	HvCallRioCompId = 10,
 	HvCallRsvd3CompId = 11,
 	HvCallRsvd2CompId = 12,
 	HvCallRsvd1CompId = 13,
 	HvCallMaxCompId = 14,
-	HvPrimaryCallCompId = 0,    
+	HvPrimaryCallCompId = 0,
 	HvPrimaryCallCfgCompId = 1,
-	HvPrimaryCallPciCompId = 2,    
+	HvPrimaryCallPciCompId = 2,
 	HvPrimaryCallSmCompId = 3,
 	HvPrimaryCallSpdCompId = 4,
 	HvPrimaryCallXmCompId = 5,
-	HvPrimaryCallRioCompId = 6, 
+	HvPrimaryCallRioCompId = 6,
 	HvPrimaryCallRsvd7CompId = 7,
 	HvPrimaryCallRsvd6CompId = 8,
 	HvPrimaryCallRsvd5CompId = 9,
@@ -116,7 +102,7 @@
 	HvPrimaryCallRsvd3CompId = 11,
 	HvPrimaryCallRsvd2CompId = 12,
 	HvPrimaryCallRsvd1CompId = 13,
-	HvPrimaryCallMaxCompId = HvCallMaxCompId     
+	HvPrimaryCallMaxCompId = HvCallMaxCompId
 };
 
 struct HvLpBufferList {
diff --git a/include/asm-ppc64/iSeries/IoHriMainStore.h b/include/asm-ppc64/iSeries/IoHriMainStore.h
index ff00e86..45ed3ea 100644
--- a/include/asm-ppc64/iSeries/IoHriMainStore.h
+++ b/include/asm-ppc64/iSeries/IoHriMainStore.h
@@ -1,17 +1,17 @@
 /*
  * IoHriMainStore.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -21,7 +21,7 @@
 #define _IOHRIMAINSTORE_H
 
 /* Main Store Vpd for Condor,iStar,sStar */
-struct IoHriMainStoreSegment4 {    
+struct IoHriMainStoreSegment4 {
 	u8	msArea0Exists:1;
 	u8	msArea1Exists:1;
 	u8	msArea2Exists:1;
@@ -51,7 +51,7 @@
 	u8	msArea1HasRiserVpd:1;
 	u8	msArea2HasRiserVpd:1;
 	u8	msArea3HasRiserVpd:1;
-	u8	reserved5:4;	
+	u8	reserved5:4;
 	u8	reserved6;
 	u16	reserved7;
 
@@ -82,8 +82,8 @@
 };
 
 struct IoHriMainStoreAdrRangeBlock {
-	void *	blockStart      __attribute((packed));
-	void *	blockEnd        __attribute((packed));
+	void	*blockStart      __attribute((packed));
+	void	*blockEnd        __attribute((packed));
 	u32	blockProcChipId __attribute((packed));
 };
 
@@ -102,7 +102,7 @@
 	u32	procNodeId			__attribute((packed));
 
 	u32	numAdrRangeBlocks		__attribute((packed));
-	struct IoHriMainStoreAdrRangeBlock xAdrRangeBlock[MaxAreaAdrRangeBlocks] __attribute((packed));
+	struct IoHriMainStoreAdrRangeBlock xAdrRangeBlock[MaxAreaAdrRangeBlocks]	__attribute((packed));
 
 	struct IoHriMainStoreChipInfo1	chipInfo0	__attribute((packed));
 	struct IoHriMainStoreChipInfo1	chipInfo1	__attribute((packed));
@@ -113,17 +113,17 @@
 	struct IoHriMainStoreChipInfo1	chipInfo6	__attribute((packed));
 	struct IoHriMainStoreChipInfo1	chipInfo7	__attribute((packed));
 
-	void *   msRamAreaArray			__attribute((packed));
+	void	*msRamAreaArray			__attribute((packed));
 	u32	msRamAreaArrayNumEntries	__attribute((packed));
 	u32	msRamAreaArrayEntrySize		__attribute((packed));
 
 	u32	numaDimmExists			__attribute((packed));
 	u32	numaDimmFunctional		__attribute((packed));
-	void *	numaDimmArray			__attribute((packed));
+	void	*numaDimmArray			__attribute((packed));
 	u32	numaDimmArrayNumEntries		__attribute((packed));
 	u32	numaDimmArrayEntrySize		__attribute((packed));
 
-	struct IoHriMainStoreVpdIdData  idData	__attribute((packed));
+	struct IoHriMainStoreVpdIdData idData	__attribute((packed));
 
 	u64	powerData			__attribute((packed));
 	u64	cardAssemblyPartNum		__attribute((packed));
@@ -143,7 +143,7 @@
 };
 
 
-struct IoHriMainStoreSegment5 {    
+struct IoHriMainStoreSegment5 {
 	u16	reserved1;
 	u8	reserved2;
 	u8	msVpdFormat;
@@ -151,17 +151,16 @@
 	u32	totalMainStore;
 	u64	maxConfiguredMsAdr;
 
-	struct IoHriMainStoreArea4*	msAreaArray;
+	struct IoHriMainStoreArea4	*msAreaArray;
 	u32	msAreaArrayNumEntries;
 	u32	msAreaArrayEntrySize;
 
-	u32	msAreaExists;    
+	u32	msAreaExists;
 	u32	msAreaFunctional;
 
 	u64	reserved3;
 };
 
+extern u64	xMsVpd[];
 
-
-#endif // _IOHRIMAINSTORE_H
-
+#endif	/* _IOHRIMAINSTORE_H */
diff --git a/include/asm-ppc64/iSeries/IoHriProcessorVpd.h b/include/asm-ppc64/iSeries/IoHriProcessorVpd.h
index 9654338..73b73d8 100644
--- a/include/asm-ppc64/iSeries/IoHriProcessorVpd.h
+++ b/include/asm-ppc64/iSeries/IoHriProcessorVpd.h
@@ -1,17 +1,17 @@
 /*
  * IoHriProcessorVpd.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,16 +19,12 @@
 #ifndef _IOHRIPROCESSORVPD_H
 #define _IOHRIPROCESSORVPD_H
 
-//===================================================================
-//
-//	This struct maps Processor Vpd that is DMAd to SLIC by CSP 
-//
-
 #include <asm/types.h>
 
-struct IoHriProcessorVpd
-{
-
+/*
+ * This struct maps Processor Vpd that is DMAd to SLIC by CSP
+ */
+struct IoHriProcessorVpd {
 	u8	xFormat;		// VPD format indicator		x00-x00
 	u8	xProcStatus:8;		// Processor State		x01-x01
 	u8	xSecondaryThreadCount;	// Secondary thread cnt		x02-x02
@@ -40,12 +36,12 @@
 	u16	xRsvd2;			// Reserved			x06-x07
 	u32	xHwNodeId;		// Hardware node id		x08-x0B
 	u32	xHwProcId;		// Hardware processor id	x0C-x0F
-	
+
 	u32	xTypeNum;		// Card Type/CCIN number	x10-x13
 	u32	xModelNum;		// Model/Feature number		x14-x17
 	u64	xSerialNum;		// Serial number		x18-x1F
-	char xPartNum[12];		// Book Part or FPU number	x20-x2B
-	char xMfgID[4];			// Manufacturing ID		x2C-x2F
+	char	xPartNum[12];		// Book Part or FPU number	x20-x2B
+	char	xMfgID[4];		// Manufacturing ID		x2C-x2F
 
 	u32	xProcFreq;		// Processor Frequency		x30-x33
 	u32	xTimeBaseFreq;		// Time Base Frequency		x34-x37
@@ -71,7 +67,7 @@
 	u32	xDataL3CacheSizeKB;	// L3 data cache size in KB	x80-x83
 	u32	xDataL3CacheLineSize;	// L3 data cache block size	x84-x87
 	u64	xRsvd6;			// Reserved			x88-x8F
-   
+
 	u64	xFruLabel;		// Card Location Label		x90-x97
 	u8	xSlotsOnCard;		// Slots on card (0=no slots)	x98-x98
 	u8	xPartLocFlag;		// Location flag (0-pluggable 1-imbedded) x99-x99
@@ -79,10 +75,12 @@
 	u8	xSmartCardPortNo;	// Smart card port number	x9C-x9C
 	u8	xRsvd7;			// Reserved			x9D-x9D
 	u16	xFrameIdAndRackUnit;	// Frame ID and rack unit adr	x9E-x9F
-    
+
 	u8	xRsvd8[24];		// Reserved			xA0-xB7
 
-	char xProcSrc[72];		// CSP format SRC		xB8-xFF
+	char	xProcSrc[72];		// CSP format SRC		xB8-xFF
 };
 
+extern struct IoHriProcessorVpd	xIoHriProcessorVpd[];
+
 #endif /* _IOHRIPROCESSORVPD_H */
diff --git a/include/asm-ppc64/iSeries/ItExtVpdPanel.h b/include/asm-ppc64/iSeries/ItExtVpdPanel.h
index dee6b12..4c546a8 100644
--- a/include/asm-ppc64/iSeries/ItExtVpdPanel.h
+++ b/include/asm-ppc64/iSeries/ItExtVpdPanel.h
@@ -1,17 +1,17 @@
 /*
  * ItExtVpdPanel.h
  * Copyright (C) 2002  Dave Boutcher IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -20,39 +20,33 @@
 #define _ITEXTVPDPANEL_H
 
 /*
- *
- *	This struct maps the panel information 
+ *	This struct maps the panel information
  *
  * Warning:
  *	This data must match the architecture for the panel information
- *
  */
 
-
-/*-------------------------------------------------------------------
- * Standard Includes
- *------------------------------------------------------------------- 
-*/
 #include <asm/types.h>
 
-struct ItExtVpdPanel
-{
-  // Definition of the Extended Vpd On Panel Data Area
-  char                      systemSerial[8];
-  char                      mfgID[4];
-  char                      reserved1[24];
-  char                      machineType[4];
-  char                      systemID[6];
-  char                      somUniqueCnt[4];
-  char                      serialNumberCount;
-  char                      reserved2[7];
-  u16                       bbu3;
-  u16                       bbu2;
-  u16                       bbu1;
-  char                      xLocationLabel[8];
-  u8                        xRsvd1[6];
-  u16                       xFrameId;
-  u8                        xRsvd2[48];
+struct ItExtVpdPanel {
+	/* Definition of the Extended Vpd On Panel Data Area */
+	char	systemSerial[8];
+	char	mfgID[4];
+	char	reserved1[24];
+	char	machineType[4];
+	char	systemID[6];
+	char	somUniqueCnt[4];
+	char	serialNumberCount;
+	char	reserved2[7];
+	u16	bbu3;
+	u16	bbu2;
+	u16	bbu1;
+	char	xLocationLabel[8];
+	u8	xRsvd1[6];
+	u16	xFrameId;
+	u8	xRsvd2[48];
 };
 
-#endif /* _ITEXTVPDPANEL_H  */
+extern struct ItExtVpdPanel	xItExtVpdPanel;
+
+#endif /* _ITEXTVPDPANEL_H */
diff --git a/include/asm-ppc64/iSeries/ItIplParmsReal.h b/include/asm-ppc64/iSeries/ItIplParmsReal.h
index 4d8b430..ae3417d 100644
--- a/include/asm-ppc64/iSeries/ItIplParmsReal.h
+++ b/include/asm-ppc64/iSeries/ItIplParmsReal.h
@@ -1,17 +1,17 @@
 /*
  * ItIplParmsReal.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,58 +19,53 @@
 #ifndef _ITIPLPARMSREAL_H
 #define _ITIPLPARMSREAL_H
 
-//==============================================================================
-//
-//	This struct maps the IPL Parameters DMA'd from the SP.                  
-//
-// Warning:
-//	This data must map in exactly 64 bytes and match the architecture for
-//	the IPL parms
-//
-//=============================================================================
+/*
+ *	This struct maps the IPL Parameters DMA'd from the SP.
+ *
+ * Warning:
+ *	This data must map in exactly 64 bytes and match the architecture for
+ *	the IPL parms
+ */
 
-
-//-------------------------------------------------------------------
-// Standard Includes
-//-------------------------------------------------------------------
 #include <asm/types.h>
 
-struct ItIplParmsReal
-{
-	u8	xFormat;		// Defines format of IplParms		x00-x00
-	u8	xRsvd01:6;		// Reserved				x01-x01
-	u8	xAlternateSearch:1;	// Alternate search indicator		...
-	u8	xUaSupplied:1;		// UA Supplied on programmed IPL	...
-	u8	xLsUaFormat;		// Format byte for UA			x02-x02
-	u8	xRsvd02;		// Reserved				x03-x03
-	u32	xLsUa;			// LS UA				x04-x07
-	u32	xUnusedLsLid;		// First OS LID to load			x08-x0B
-	u16	xLsBusNumber;		// LS Bus Number			x0C-x0D
-	u8	xLsCardAdr;		// LS Card Address			x0E-x0E
-	u8	xLsBoardAdr;		// LS Board Address			x0F-x0F
-	u32	xRsvd03;		// Reserved				x10-x13
-	u8	xSpcnPresent:1;		// SPCN present				x14-x14
-	u8	xCpmPresent:1;		// CPM present				...
-	u8	xRsvd04:6;		// Reserved				...
-	u8	xRsvd05:4;		// Reserved				x15-x15
-	u8	xKeyLock:4;		// Keylock setting			...
-	u8	xRsvd06:6;		// Reserved				x16-x16
-	u8	xIplMode:2;		// Ipl mode (A|B|C|D)			...
-	u8	xHwIplType;		// Fast v slow v slow EC HW IPL		x17-x17
-	u16	xCpmEnabledIpl:1;	// CPM in effect when IPL initiated	x18-x19
-	u16	xPowerOnResetIpl:1;	// Indicate POR condition		...
-	u16	xMainStorePreserved:1;	// Main Storage is preserved		...
-	u16	xRsvd07:13;		// Reserved				...
-	u16	xIplSource:16;		// Ipl source				x1A-x1B
-	u8	xIplReason:8;		// Reason for this IPL			x1C-x1C
-	u8	xRsvd08;		// Reserved				x1D-x1D
-	u16	xRsvd09;		// Reserved				x1E-x1F
-	u16	xSysBoxType;		// System Box Type			x20-x21
-	u16	xSysProcType;		// System Processor Type		x22-x23
-	u32	xRsvd10;		// Reserved				x24-x27
-	u64	xRsvd11;		// Reserved				x28-x2F
-	u64	xRsvd12;		// Reserved				x30-x37
-	u64	xRsvd13;		// Reserved				x38-x3F
+struct ItIplParmsReal {
+	u8	xFormat;		// Defines format of IplParms	x00-x00
+	u8	xRsvd01:6;		// Reserved			x01-x01
+	u8	xAlternateSearch:1;	// Alternate search indicator	...
+	u8	xUaSupplied:1;		// UA Supplied on programmed IPL...
+	u8	xLsUaFormat;		// Format byte for UA		x02-x02
+	u8	xRsvd02;		// Reserved			x03-x03
+	u32	xLsUa;			// LS UA			x04-x07
+	u32	xUnusedLsLid;		// First OS LID to load		x08-x0B
+	u16	xLsBusNumber;		// LS Bus Number		x0C-x0D
+	u8	xLsCardAdr;		// LS Card Address		x0E-x0E
+	u8	xLsBoardAdr;		// LS Board Address		x0F-x0F
+	u32	xRsvd03;		// Reserved			x10-x13
+	u8	xSpcnPresent:1;		// SPCN present			x14-x14
+	u8	xCpmPresent:1;		// CPM present			...
+	u8	xRsvd04:6;		// Reserved			...
+	u8	xRsvd05:4;		// Reserved			x15-x15
+	u8	xKeyLock:4;		// Keylock setting		...
+	u8	xRsvd06:6;		// Reserved			x16-x16
+	u8	xIplMode:2;		// Ipl mode (A|B|C|D)		...
+	u8	xHwIplType;		// Fast v slow v slow EC HW IPL	x17-x17
+	u16	xCpmEnabledIpl:1;	// CPM in effect when IPL initiatedx18-x19
+	u16	xPowerOnResetIpl:1;	// Indicate POR condition	...
+	u16	xMainStorePreserved:1;	// Main Storage is preserved	...
+	u16	xRsvd07:13;		// Reserved			...
+	u16	xIplSource:16;		// Ipl source			x1A-x1B
+	u8	xIplReason:8;		// Reason for this IPL		x1C-x1C
+	u8	xRsvd08;		// Reserved			x1D-x1D
+	u16	xRsvd09;		// Reserved			x1E-x1F
+	u16	xSysBoxType;		// System Box Type		x20-x21
+	u16	xSysProcType;		// System Processor Type	x22-x23
+	u32	xRsvd10;		// Reserved			x24-x27
+	u64	xRsvd11;		// Reserved			x28-x2F
+	u64	xRsvd12;		// Reserved			x30-x37
+	u64	xRsvd13;		// Reserved			x38-x3F
 };
 
+extern struct ItIplParmsReal	xItIplParmsReal;
+
 #endif /* _ITIPLPARMSREAL_H */
diff --git a/include/asm-ppc64/iSeries/ItLpNaca.h b/include/asm-ppc64/iSeries/ItLpNaca.h
index 5baffdd..225d017 100644
--- a/include/asm-ppc64/iSeries/ItLpNaca.h
+++ b/include/asm-ppc64/iSeries/ItLpNaca.h
@@ -1,17 +1,17 @@
 /*
  * ItLpNaca.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,18 +19,15 @@
 #ifndef _ITLPNACA_H
 #define _ITLPNACA_H
 
-//=============================================================================
-//
-//	This control block contains the data that is shared between the
-//	hypervisor (PLIC) and the OS.
-//
-//=============================================================================
+#include <linux/types.h>
 
-struct ItLpNaca
-{
-//=============================================================================
+/*
+ *	This control block contains the data that is shared between the
+ *	hypervisor (PLIC) and the OS.
+ */
+
+struct ItLpNaca {
 // CACHE_LINE_1 0x0000 - 0x007F Contains read-only data
-//=============================================================================
 	u32	xDesc;			// Eye catcher			x00-x03
 	u16	xSize;			// Size of this class		x04-x05
 	u16	xIntHdlrOffset;		// Offset to IntHdlr array	x06-x07
@@ -59,30 +56,25 @@
 	u64	xLoadAreaAddr;		// ER address of load area	x28-x2F
 	u32	xLoadAreaChunks;	// Chunks for the load area	x30-x33
 	u32	xPaseSysCallCRMask;	// Mask used to test CR before  x34-x37
-	// doing an ASR switch on PASE
-	// system call.
-	u64	xSlicSegmentTablePtr;   // Pointer to Slic seg table.   x38-x3f
-	u8	xRsvd1_4[64];		//         			x40-x7F 
-   
-//=============================================================================
+					// doing an ASR switch on PASE
+					// system call.
+	u64	xSlicSegmentTablePtr;	// Pointer to Slic seg table.   x38-x3f
+	u8	xRsvd1_4[64];		//				x40-x7F
+
 // CACHE_LINE_2 0x0080 - 0x00FF Contains local read-write data
-//=============================================================================
 	u8	xRsvd2_0[128];		// Reserved			x00-x7F
 
-//=============================================================================
 // CACHE_LINE_3-6 0x0100 - 0x02FF Contains LP Queue indicators
-// NB: Padding required to keep xInterrruptHdlr at x300 which is required 
+// NB: Padding required to keep xInterrruptHdlr at x300 which is required
 // for v4r4 PLIC.
-//=============================================================================
 	u8	xOldLpQueue[128];	// LP Queue needed for v4r4	100-17F
 	u8	xRsvd3_0[384];		// Reserved			180-2FF
-//=============================================================================
+
 // CACHE_LINE_7-8 0x0300 - 0x03FF Contains the address of the OS interrupt
 //  handlers
-//=============================================================================
 	u64	xInterruptHdlr[32];	// Interrupt handlers		300-x3FF
 };
 
-//=============================================================================
+extern struct ItLpNaca		itLpNaca;
 
 #endif /* _ITLPNACA_H */
diff --git a/include/asm-ppc64/iSeries/ItLpQueue.h b/include/asm-ppc64/iSeries/ItLpQueue.h
index 4f4dde2..393299e 100644
--- a/include/asm-ppc64/iSeries/ItLpQueue.h
+++ b/include/asm-ppc64/iSeries/ItLpQueue.h
@@ -1,17 +1,17 @@
 /*
  * ItLpQueue.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,54 +19,54 @@
 #ifndef _ITLPQUEUE_H
 #define _ITLPQUEUE_H
 
-//=============================================================================
-//
-//	This control block defines the simple LP queue structure that is 
-//	shared between the hypervisor (PLIC) and the OS in order to send 
-//	events to an LP.  
-//    
+/*
+ *	This control block defines the simple LP queue structure that is
+ *	shared between the hypervisor (PLIC) and the OS in order to send
+ *	events to an LP.
+ */
 
 #include <asm/types.h>
 #include <asm/ptrace.h>
 
 struct HvLpEvent;
 
-#define ITMaxLpQueues 8
+#define ITMaxLpQueues	8
 
 #define NotUsed		0	// Queue will not be used by PLIC
 #define DedicatedIo	1	// Queue dedicated to IO processor specified
 #define DedicatedLp	2	// Queue dedicated to LP specified
 #define Shared		3	// Queue shared for both IO and LP
 
-#define LpEventStackSize 4096
-#define LpEventMaxSize   256
-#define LpEventAlign	 64
+#define LpEventStackSize	4096
+#define LpEventMaxSize		256
+#define LpEventAlign		64
 
-struct ItLpQueue
-{
-//
-//  The xSlicCurEventPtr is the pointer to the next event stack entry that will
-//  become valid.  The OS must peek at this entry to determine if it is valid.
-//  PLIC will set the valid indicator as the very last store into that entry.
-//
-//  When the OS has completed processing of the event then it will mark the event
-//  as invalid so that PLIC knows it can store into that event location again.
-//
-// If the event stack fills and there are overflow events, then PLIC will set 
-// the xPlicOverflowIntPending flag in which case the OS will have to fetch the 
-// additional LP events once they have drained the event stack.
-//
-// The first 16-bytes are known by both the OS and PLIC.  The remainder of the
-// cache line is for use by the OS.
-//
-//=============================================================================
+struct ItLpQueue {
+/*
+ * The xSlicCurEventPtr is the pointer to the next event stack entry
+ * that will become valid.  The OS must peek at this entry to determine
+ * if it is valid.  PLIC will set the valid indicator as the very last
+ * store into that entry.
+ *
+ * When the OS has completed processing of the event then it will mark
+ * the event as invalid so that PLIC knows it can store into that event
+ * location again.
+ *
+ * If the event stack fills and there are overflow events, then PLIC
+ * will set the xPlicOverflowIntPending flag in which case the OS will
+ * have to fetch the additional LP events once they have drained the
+ * event stack.
+ *
+ * The first 16-bytes are known by both the OS and PLIC.  The remainder
+ * of the cache line is for use by the OS.
+ */
 	u8	xPlicOverflowIntPending;// 0x00 Overflow events are pending
 	u8	xPlicStatus;		// 0x01 DedicatedIo or DedicatedLp or NotUsed
 	u16	xSlicLogicalProcIndex;	// 0x02 Logical Proc Index for correlation
 	u8	xPlicRsvd[12];		// 0x04
-	char*	xSlicCurEventPtr;	// 0x10
-	char*	xSlicLastValidEventPtr;	// 0x18
-	char*	xSlicEventStackPtr;	// 0x20
+	char	*xSlicCurEventPtr;	// 0x10
+	char	*xSlicLastValidEventPtr; // 0x18
+	char	*xSlicEventStackPtr;	// 0x20
 	u8	xIndex;			// 0x28 unique sequential index.
 	u8	xSlicRsvd[3];		// 0x29-2b
 	u32	xInUseWord;		// 0x2C
@@ -76,17 +76,9 @@
 
 extern struct ItLpQueue xItLpQueue;
 
-extern struct HvLpEvent * ItLpQueue_getNextLpEvent( struct ItLpQueue * );
-extern int ItLpQueue_isLpIntPending( struct ItLpQueue * ); 
-extern unsigned ItLpQueue_process( struct ItLpQueue *, struct pt_regs * );
-extern void ItLpQueue_clearValid( struct HvLpEvent * );
-
-static __inline__ void process_iSeries_events( void )
-{
-	__asm__ __volatile__ (
-	"	li	0,0x5555	\n\
-		sc"
-	: : : "r0", "r3" );	
-}
+extern struct HvLpEvent *ItLpQueue_getNextLpEvent(struct ItLpQueue *);
+extern int ItLpQueue_isLpIntPending(struct ItLpQueue *);
+extern unsigned ItLpQueue_process(struct ItLpQueue *, struct pt_regs *);
+extern void ItLpQueue_clearValid(struct HvLpEvent *);
 
 #endif /* _ITLPQUEUE_H */
diff --git a/include/asm-ppc64/iSeries/ItLpRegSave.h b/include/asm-ppc64/iSeries/ItLpRegSave.h
index dafc4c8..1b3087e 100644
--- a/include/asm-ppc64/iSeries/ItLpRegSave.h
+++ b/include/asm-ppc64/iSeries/ItLpRegSave.h
@@ -1,17 +1,17 @@
 /*
  * ItLpRegSave.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,33 +19,30 @@
 #ifndef _ITLPREGSAVE_H
 #define _ITLPREGSAVE_H
 
-//=====================================================================================
-//
-//	This control block contains the data that is shared between PLIC
-//	and the OS
-//    
-//
+/*
+ * This control block contains the data that is shared between PLIC
+ * and the OS
+ */
 
-struct ItLpRegSave
-{
+struct ItLpRegSave {
 	u32	xDesc;		// Eye catcher  "LpRS" ebcdic	000-003
 	u16	xSize;		// Size of this class		004-005
 	u8	xInUse;         // Area is live                 006-007
-	u8	xRsvd1[9]; 	// Reserved			007-00F
+	u8	xRsvd1[9];	// Reserved			007-00F
 
-	u8      xFixedRegSave[352]; // Fixed Register Save Area 010-16F 
+	u8      xFixedRegSave[352]; // Fixed Register Save Area 010-16F
 	u32	xCTRL;		// Control Register		170-173
-	u32	xDEC;		// Decrementer			174-177    
+	u32	xDEC;		// Decrementer			174-177
 	u32	xFPSCR;		// FP Status and Control Reg	178-17B
 	u32	xPVR;		// Processor Version Number	17C-17F
-    
+
 	u64	xMMCR0;		// Monitor Mode Control Reg 0	180-187
 	u32	xPMC1;		// Perf Monitor Counter 1	188-18B
 	u32	xPMC2;		// Perf Monitor Counter 2	18C-18F
 	u32	xPMC3;		// Perf Monitor Counter 3	190-193
 	u32	xPMC4;		// Perf Monitor Counter 4	194-197
 	u32	xPIR;		// Processor ID Reg		198-19B
-    
+
 	u32	xMMCR1;		// Monitor Mode Control Reg 1	19C-19F
 	u32	xMMCRA;		// Monitor Mode Control Reg A	1A0-1A3
 	u32	xPMC5;		// Perf Monitor Counter 5	1A4-1A7
@@ -57,17 +54,17 @@
 	u32	xRsvd;          // Reserved                     1BC-1BF
 
 	u64	xACCR;		// Address Compare Control Reg	1C0-1C7
-	u64	xIMR;		// Instruction Match Register	1C8-1CF    
-	u64	xSDR1;		// Storage Description Reg 1	1D0-1D7    
+	u64	xIMR;		// Instruction Match Register	1C8-1CF
+	u64	xSDR1;		// Storage Description Reg 1	1D0-1D7
 	u64	xSPRG0;		// Special Purpose Reg General0	1D8-1DF
 	u64	xSPRG1;		// Special Purpose Reg General1	1E0-1E7
 	u64	xSPRG2;		// Special Purpose Reg General2	1E8-1EF
 	u64	xSPRG3;		// Special Purpose Reg General3	1F0-1F7
 	u64	xTB;		// Time Base Register		1F8-1FF
-   
+
 	u64	xFPR[32];	// Floating Point Registers	200-2FF
 
-	u64	xMSR;		// Machine State Register  	300-307
+	u64	xMSR;		// Machine State Register	300-307
 	u64	xNIA;		// Next Instruction Address	308-30F
 
 	u64	xDABR;		// Data Address Breakpoint Reg	310-317
@@ -76,8 +73,8 @@
 	u64	xHID0;		// HW Implementation Dependent0	320-327
 
 	u64	xHID4;		// HW Implementation Dependent4	328-32F
-	u64	xSCOMd;		// SCON Data Reg (SPRG4)       	330-337
-	u64	xSCOMc;		// SCON Command Reg (SPRG5)    	338-33F
+	u64	xSCOMd;		// SCON Data Reg (SPRG4)	330-337
+	u64	xSCOMc;		// SCON Command Reg (SPRG5)	338-33F
 	u64	xSDAR;		// Sample Data Address Register	340-347
 	u64	xSIAR;		// Sample Inst Address Register	348-34F
 
diff --git a/include/asm-ppc64/iSeries/ItSpCommArea.h b/include/asm-ppc64/iSeries/ItSpCommArea.h
index f1b56f9..5535f82 100644
--- a/include/asm-ppc64/iSeries/ItSpCommArea.h
+++ b/include/asm-ppc64/iSeries/ItSpCommArea.h
@@ -1,29 +1,27 @@
 /*
  * ItSpCommArea.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  */
 
-
 #ifndef _ITSPCOMMAREA_H
 #define _ITSPCOMMAREA_H
 
 
-struct SpCommArea
-{
+struct SpCommArea {
 	u32	xDesc;			// Descriptor (only in new formats)	000-003
 	u8	xFormat;		// Format (only in new formats)		004-004
 	u8	xRsvd1[11];		// Reserved				005-00F
diff --git a/include/asm-ppc64/iSeries/ItVpdAreas.h b/include/asm-ppc64/iSeries/ItVpdAreas.h
index d120439..71b3ad2 100644
--- a/include/asm-ppc64/iSeries/ItVpdAreas.h
+++ b/include/asm-ppc64/iSeries/ItVpdAreas.h
@@ -1,17 +1,17 @@
 /*
  * ItVpdAreas.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -19,78 +19,71 @@
 #ifndef _ITVPDAREAS_H
 #define _ITVPDAREAS_H
 
-//=====================================================================================
-//
-//      This file defines the address and length of all of the VPD area passed to
-//	the OS from PLIC (most of which start from the SP).
-//
+/*
+ * This file defines the address and length of all of the VPD area passed to
+ * the OS from PLIC (most of which start from the SP).
+ */
 
 #include <asm/types.h>
 
-// VPD Entry index is carved in stone - cannot be changed (easily).
-#define ItVpdCecVpd				   0
-#define ItVpdDynamicSpace			   1
-#define ItVpdExtVpd				   2
-#define ItVpdExtVpdOnPanel			   3
-#define ItVpdFirstPaca				   4
-#define ItVpdIoVpd				   5
-#define ItVpdIplParms				   6
-#define ItVpdMsVpd				   7
-#define ItVpdPanelVpd				   8
-#define ItVpdLpNaca				   9
-#define ItVpdBackplaneAndMaybeClockCardVpd        10 
-#define ItVpdRecoveryLogBuffer		          11
-#define ItVpdSpCommArea				  12
-#define ItVpdSpLogBuffer			  13
-#define ItVpdSpLogBufferSave			  14
-#define ItVpdSpCardVpd				  15
-#define ItVpdFirstProcVpd			  16	
-#define ItVpdApModelVpd				  17
-#define ItVpdClockCardVpd			  18
-#define ItVpdBusExtCardVpd			  19
-#define ItVpdProcCapacityVpd			  20
-#define ItVpdInteractiveCapacityVpd		  21
-#define ItVpdFirstSlotLabel			  22
-#define ItVpdFirstLpQueue			  23
-#define ItVpdFirstL3CacheVpd			  24	
-#define ItVpdFirstProcFruVpd			  25
+/* VPD Entry index is carved in stone - cannot be changed (easily). */
+#define ItVpdCecVpd				0
+#define ItVpdDynamicSpace			1
+#define ItVpdExtVpd				2
+#define ItVpdExtVpdOnPanel			3
+#define ItVpdFirstPaca				4
+#define ItVpdIoVpd				5
+#define ItVpdIplParms				6
+#define ItVpdMsVpd				7
+#define ItVpdPanelVpd				8
+#define ItVpdLpNaca				9
+#define ItVpdBackplaneAndMaybeClockCardVpd	10
+#define ItVpdRecoveryLogBuffer			11
+#define ItVpdSpCommArea				12
+#define ItVpdSpLogBuffer			13
+#define ItVpdSpLogBufferSave			14
+#define ItVpdSpCardVpd				15
+#define ItVpdFirstProcVpd			16
+#define ItVpdApModelVpd				17
+#define ItVpdClockCardVpd			18
+#define ItVpdBusExtCardVpd			19
+#define ItVpdProcCapacityVpd			20
+#define ItVpdInteractiveCapacityVpd		21
+#define ItVpdFirstSlotLabel			22
+#define ItVpdFirstLpQueue			23
+#define ItVpdFirstL3CacheVpd			24
+#define ItVpdFirstProcFruVpd			25
 
-#define ItVpdMaxEntries				  26
+#define ItVpdMaxEntries				26
+
+#define ItDmaMaxEntries				10
+
+#define ItVpdAreasMaxSlotLabels			192
 
 
-#define ItDmaMaxEntries				  10
-
-#define ItVpdAreasMaxSlotLabels		 192 
-
-
-struct SlicVpdAdrs {
-	u32	pad1;
-	void *  vpdAddr;
+struct ItVpdAreas {
+	u32	xSlicDesc;		// Descriptor			000-003
+	u16	xSlicSize;		// Size of this control block	004-005
+	u16	xPlicAdjustVpdLens:1;	// Flag to indicate new interface006-007
+	u16	xRsvd1:15;		// Reserved bits		...
+	u16	xSlicVpdEntries;	// Number of VPD entries	008-009
+	u16	xSlicDmaEntries;	// Number of DMA entries	00A-00B
+	u16	xSlicMaxLogicalProcs;	// Maximum logical processors	00C-00D
+	u16	xSlicMaxPhysicalProcs;	// Maximum physical processors	00E-00F
+	u16	xSlicDmaToksOffset;	// Offset into this of array	010-011
+	u16	xSlicVpdAdrsOffset;	// Offset into this of array	012-013
+	u16	xSlicDmaLensOffset;	// Offset into this of array	014-015
+	u16	xSlicVpdLensOffset;	// Offset into this of array	016-017
+	u16	xSlicMaxSlotLabels;	// Maximum number of slot labels018-019
+	u16	xSlicMaxLpQueues;	// Maximum number of LP Queues	01A-01B
+	u8	xRsvd2[4];		// Reserved			01C-01F
+	u64	xRsvd3[12];		// Reserved			020-07F
+	u32	xPlicDmaLens[ItDmaMaxEntries];// Array of DMA lengths	080-0A7
+	u32	xPlicDmaToks[ItDmaMaxEntries];// Array of DMA tokens	0A8-0CF
+	u32	xSlicVpdLens[ItVpdMaxEntries];// Array of VPD lengths	0D0-12F
+	void	*xSlicVpdAdrs[ItVpdMaxEntries];// Array of VPD buffers	130-1EF
 };
 
-
-struct	ItVpdAreas
-{
-	u32	xSlicDesc;		// Descriptor				000-003
-	u16	xSlicSize;		// Size of this control block		004-005
-	u16	xPlicAdjustVpdLens:1;	// Flag to indicate new interface 	006-007
-	u16	xRsvd1:15;		// Reserved bits			...
-	u16	xSlicVpdEntries;	// Number of VPD entries		008-009
-	u16	xSlicDmaEntries;	// Number of DMA entries		00A-00B
-	u16	xSlicMaxLogicalProcs;	// Maximum logical processors		00C-00D
-	u16	xSlicMaxPhysicalProcs;	// Maximum physical processors		00E-00F
-	u16	xSlicDmaToksOffset;	// Offset into this of array		010-011
-	u16	xSlicVpdAdrsOffset;	// Offset into this of array		012-013
-	u16	xSlicDmaLensOffset;	// Offset into this of array		014-015
-	u16	xSlicVpdLensOffset;	// Offset into this of array		016-017
-	u16	xSlicMaxSlotLabels;	// Maximum number of slot labels	018-019
-	u16	xSlicMaxLpQueues;	// Maximum number of LP Queues		01A-01B
-	u8	xRsvd2[4];		// Reserved				01C-01F
-	u64	xRsvd3[12];		// Reserved				020-07F
-	u32	xPlicDmaLens[ItDmaMaxEntries];// Array of DMA lengths		080-0A7
-	u32	xPlicDmaToks[ItDmaMaxEntries];// Array of DMA tokens		0A8-0CF
-	u32	xSlicVpdLens[ItVpdMaxEntries];// Array of VPD lengths		0D0-12F
-	void * xSlicVpdAdrs[ItVpdMaxEntries];// Array of VPD buffers	130-1EF
-};
+extern struct ItVpdAreas	itVpdAreas;
 
 #endif /* _ITVPDAREAS_H */
diff --git a/include/asm-ppc64/iSeries/LparData.h b/include/asm-ppc64/iSeries/LparData.h
deleted file mode 100644
index e54f3b6..0000000
--- a/include/asm-ppc64/iSeries/LparData.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * LparData.h
- * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- * 
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
- */
-
-#ifndef _LPARDATA_H
-#define _LPARDATA_H
-
-#include <asm/types.h>
-#include <asm/page.h>
-#include <asm/abs_addr.h>
-
-#include <asm/iSeries/ItLpNaca.h>
-#include <asm/iSeries/ItLpRegSave.h>
-#include <asm/iSeries/HvReleaseData.h>
-#include <asm/iSeries/LparMap.h>
-#include <asm/iSeries/ItVpdAreas.h>
-#include <asm/iSeries/ItIplParmsReal.h>
-#include <asm/iSeries/ItExtVpdPanel.h>
-#include <asm/iSeries/ItLpQueue.h>
-#include <asm/iSeries/IoHriProcessorVpd.h>
-
-extern struct LparMap	xLparMap;
-extern struct HvReleaseData hvReleaseData;
-extern struct ItLpNaca	itLpNaca;
-extern struct ItIplParmsReal xItIplParmsReal;
-extern struct ItExtVpdPanel xItExtVpdPanel;
-extern struct IoHriProcessorVpd xIoHriProcessorVpd[];
-extern struct ItLpQueue xItLpQueue;
-extern struct ItVpdAreas itVpdAreas;
-extern u64    xMsVpd[];
-extern struct msChunks msChunks;
-
-
-#endif /* _LPARDATA_H */
diff --git a/include/asm-ppc64/iSeries/LparMap.h b/include/asm-ppc64/iSeries/LparMap.h
index 075205b..038e5df 100644
--- a/include/asm-ppc64/iSeries/LparMap.h
+++ b/include/asm-ppc64/iSeries/LparMap.h
@@ -1,17 +1,17 @@
 /*
  * LparMap.h
  * Copyright (C) 2001  Mike Corrigan IBM Corporation
- * 
+ *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
@@ -21,13 +21,14 @@
 
 #include <asm/types.h>
 
-/* The iSeries hypervisor will set up mapping for one or more 
+/*
+ * The iSeries hypervisor will set up mapping for one or more
  * ESID/VSID pairs (in SLB/segment registers) and will set up
  * mappings of one or more ranges of pages to VAs.
  * We will have the hypervisor set up the ESID->VSID mapping
  * for the four kernel segments (C-F).  With shared processors,
  * the hypervisor will clear all segment registers and reload
- * these four whenever the processor is switched from one 
+ * these four whenever the processor is switched from one
  * partition to another.
  */
 
@@ -38,30 +39,31 @@
  * need to be located within the load area (if the total partition size
  * is 64 MB), but cannot be mapped.  Typically, this should specify
  * to map half (32 MB) of the load area.
- * 
- * The hypervisor will set up page table entries for the number of 
+ *
+ * The hypervisor will set up page table entries for the number of
  * pages specified.
  *
  * In 32-bit mode, the hypervisor will load all four of the
- * segment registers (identified by the low-order four bits of the 
+ * segment registers (identified by the low-order four bits of the
  * Esid field.  In 64-bit mode, the hypervisor will load one SLB
  * entry to map the Esid to the Vsid.
 */
 
-// Hypervisor initially maps 32MB of the load area 
-#define HvPagesToMap 8192
+/* Hypervisor initially maps 32MB of the load area */
+#define HvPagesToMap	8192
 
-struct LparMap
-{
-	u64	  xNumberEsids;		// Number of ESID/VSID pairs (1)
-	u64	  xNumberRanges;	// Number of VA ranges to map (1)
-	u64	  xSegmentTableOffs;	// Page number within load area of seg table (0)
-	u64	  xRsvd[5];		// Reserved (0)
-	u64	  xKernelEsid;  	// Esid used to map kernel load (0x0C00000000)	
-	u64	  xKernelVsid;		// Vsid used to map kernel load (0x0C00000000)
-	u64	  xPages;		// Number of pages to be mapped	(8192)
-	u64	  xOffset;		// Offset from start of load area (0)
-	u64	  xVPN;			// Virtual Page Number (0x000C000000000000)
+struct LparMap {
+	u64	xNumberEsids;	// Number of ESID/VSID pairs (1)
+	u64	xNumberRanges;	// Number of VA ranges to map (1)
+	u64	xSegmentTableOffs; // Page number within load area of seg table (0)
+	u64	xRsvd[5];
+	u64	xKernelEsid;	// Esid used to map kernel load (0x0C00000000)
+	u64	xKernelVsid;	// Vsid used to map kernel load (0x0C00000000)
+	u64	xPages;		// Number of pages to be mapped	(8192)
+	u64	xOffset;	// Offset from start of load area (0)
+	u64	xVPN;		// Virtual Page Number (0x000C000000000000)
 };
 
+extern struct LparMap		xLparMap;
+
 #endif /* _LPARMAP_H */
diff --git a/include/asm-ppc64/iSeries/XmPciLpEvent.h b/include/asm-ppc64/iSeries/XmPciLpEvent.h
deleted file mode 100644
index a3d27f1..0000000
--- a/include/asm-ppc64/iSeries/XmPciLpEvent.h
+++ /dev/null
@@ -1,18 +0,0 @@
-
-#ifndef	__XMPCILPEVENT_H__
-#define	__XMPCILPEVENT_H__
-
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-int XmPciLpEvent_init(void);
-void ppc_irq_dispatch_handler(struct pt_regs *regs, int irq);
-
-
-#ifdef __cplusplus
-}
-#endif
-
-#endif /* __XMPCILPEVENT_H__ */
diff --git a/include/asm-ppc64/iSeries/iSeries_io.h b/include/asm-ppc64/iSeries/iSeries_io.h
index f52b759..9f79413 100644
--- a/include/asm-ppc64/iSeries/iSeries_io.h
+++ b/include/asm-ppc64/iSeries/iSeries_io.h
@@ -5,32 +5,33 @@
 
 #ifdef CONFIG_PPC_ISERIES
 #include <linux/types.h>
-/************************************************************************/
-/* File iSeries_io.h created by Allan Trautman on Thu Dec 28 2000.      */
-/************************************************************************/
-/* Remaps the io.h for the iSeries Io                                   */
-/* Copyright (C) 20yy  Allan H Trautman, IBM Corporation                */
-/*                                                                      */
-/* This program is free software; you can redistribute it and/or modify */
-/* it under the terms of the GNU General Public License as published by */
-/* the Free Software Foundation; either version 2 of the License, or    */
-/* (at your option) any later version.                                  */
-/*                                                                      */
-/* This program is distributed in the hope that it will be useful,      */ 
-/* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
-/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
-/* GNU General Public License for more details.                         */
-/*                                                                      */
-/* You should have received a copy of the GNU General Public License    */ 
-/* along with this program; if not, write to the:                       */
-/* Free Software Foundation, Inc.,                                      */ 
-/* 59 Temple Place, Suite 330,                                          */ 
-/* Boston, MA  02111-1307  USA                                          */
-/************************************************************************/
-/* Change Activity:                                                     */
-/*   Created December 28, 2000                                          */
-/* End Change Activity                                                  */
-/************************************************************************/
+/*
+ * File iSeries_io.h created by Allan Trautman on Thu Dec 28 2000.
+ *
+ * Remaps the io.h for the iSeries Io
+ * Copyright (C) 2000  Allan H Trautman, IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the:
+ * Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330,
+ * Boston, MA  02111-1307  USA
+ *
+ * Change Activity:
+ *   Created December 28, 2000
+ * End Change Activity
+ */
+
 extern u8   iSeries_Read_Byte(const volatile void __iomem * IoAddress);
 extern u16  iSeries_Read_Word(const volatile void __iomem * IoAddress);
 extern u32  iSeries_Read_Long(const volatile void __iomem * IoAddress);
@@ -39,8 +40,10 @@
 extern void iSeries_Write_Long(u32 IoData, volatile void __iomem * IoAddress);
 
 extern void iSeries_memset_io(volatile void __iomem *dest, char x, size_t n);
-extern void iSeries_memcpy_toio(volatile void __iomem *dest, void *source, size_t n);
-extern void iSeries_memcpy_fromio(void *dest, const volatile void __iomem *source, size_t n);
+extern void iSeries_memcpy_toio(volatile void __iomem *dest, void *source,
+		size_t n);
+extern void iSeries_memcpy_fromio(void *dest,
+		const volatile void __iomem *source, size_t n);
 
 #endif /* CONFIG_PPC_ISERIES */
 #endif /* _ISERIES_IO_H */
diff --git a/include/asm-ppc64/iSeries/iSeries_irq.h b/include/asm-ppc64/iSeries/iSeries_irq.h
index ff8dded..6c9767a 100644
--- a/include/asm-ppc64/iSeries/iSeries_irq.h
+++ b/include/asm-ppc64/iSeries/iSeries_irq.h
@@ -1,19 +1,8 @@
 #ifndef	__ISERIES_IRQ_H__
 #define	__ISERIES_IRQ_H__
 
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-void iSeries_init_IRQ(void);
-int  iSeries_allocate_IRQ(HvBusNumber, HvSubBusNumber, HvAgentId);
-int  iSeries_assign_IRQ(int, HvBusNumber, HvSubBusNumber, HvAgentId);
-void iSeries_activate_IRQs(void);
-
-int XmPciLpEvent_init(void);
-
-#ifdef __cplusplus
-}
-#endif
+extern void iSeries_init_IRQ(void);
+extern int  iSeries_allocate_IRQ(HvBusNumber, HvSubBusNumber, HvAgentId);
+extern void iSeries_activate_IRQs(void);
 
 #endif /* __ISERIES_IRQ_H__ */
diff --git a/include/asm-ppc64/iSeries/iSeries_pci.h b/include/asm-ppc64/iSeries/iSeries_pci.h
index 5769cff..575f611 100644
--- a/include/asm-ppc64/iSeries/iSeries_pci.h
+++ b/include/asm-ppc64/iSeries/iSeries_pci.h
@@ -1,112 +1,88 @@
 #ifndef _ISERIES_64_PCI_H
 #define _ISERIES_64_PCI_H
 
-/************************************************************************/
-/* File iSeries_pci.h created by Allan Trautman on Tue Feb 20, 2001.    */
-/************************************************************************/
-/* Define some useful macros for the iSeries pci routines.              */
-/* Copyright (C) 2001  Allan H Trautman, IBM Corporation                */
-/*                                                                      */
-/* This program is free software; you can redistribute it and/or modify */
-/* it under the terms of the GNU General Public License as published by */
-/* the Free Software Foundation; either version 2 of the License, or    */
-/* (at your option) any later version.                                  */
-/*                                                                      */
-/* This program is distributed in the hope that it will be useful,      */ 
-/* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
-/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
-/* GNU General Public License for more details.                         */
-/*                                                                      */
-/* You should have received a copy of the GNU General Public License    */ 
-/* along with this program; if not, write to the:                       */
-/* Free Software Foundation, Inc.,                                      */ 
-/* 59 Temple Place, Suite 330,                                          */ 
-/* Boston, MA  02111-1307  USA                                          */
-/************************************************************************/
-/* Change Activity:                                                     */
-/*   Created Feb 20, 2001                                               */
-/*   Added device reset, March 22, 2001                                 */
-/*   Ported to ppc64, May 25, 2001                                      */
-/* End Change Activity                                                  */
-/************************************************************************/
+/*
+ * File iSeries_pci.h created by Allan Trautman on Tue Feb 20, 2001.
+ *
+ * Define some useful macros for the iSeries pci routines.
+ * Copyright (C) 2001  Allan H Trautman, IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the:
+ * Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330,
+ * Boston, MA  02111-1307  USA
+ *
+ * Change Activity:
+ *   Created Feb 20, 2001
+ *   Added device reset, March 22, 2001
+ *   Ported to ppc64, May 25, 2001
+ * End Change Activity
+ */
 
 #include <asm/iSeries/HvCallPci.h>
 #include <asm/abs_addr.h>
 
-struct pci_dev;				/* For Forward Reference        */
+struct pci_dev;				/* For Forward Reference */
 struct iSeries_Device_Node;
 
-/************************************************************************/
-/* Gets iSeries Bus, SubBus, DevFn using iSeries_Device_Node structure */
-/************************************************************************/
+/*
+ * Gets iSeries Bus, SubBus, DevFn using iSeries_Device_Node structure
+ */
 
 #define ISERIES_BUS(DevPtr)	DevPtr->DsaAddr.Dsa.busNumber
 #define ISERIES_SUBBUS(DevPtr)	DevPtr->DsaAddr.Dsa.subBusNumber
 #define ISERIES_DEVICE(DevPtr)	DevPtr->DsaAddr.Dsa.deviceId
 #define ISERIES_DSA(DevPtr)	DevPtr->DsaAddr.DsaAddr
-#define ISERIES_DEVFUN(DevPtr)	DevPtr->DevFn
-#define ISERIES_DEVNODE(PciDev) ((struct iSeries_Device_Node*)PciDev->sysdata)
+#define ISERIES_DEVNODE(PciDev)	((struct iSeries_Device_Node *)PciDev->sysdata)
 
 #define EADsMaxAgents 7
 
-/************************************************************************/
-/* Decodes Linux DevFn to iSeries DevFn, bridge device, or function.    */
-/* For Linux, see PCI_SLOT and PCI_FUNC in include/linux/pci.h          */
-/************************************************************************/
+/*
+ * Decodes Linux DevFn to iSeries DevFn, bridge device, or function.
+ * For Linux, see PCI_SLOT and PCI_FUNC in include/linux/pci.h
+ */
 
-#define ISERIES_PCI_AGENTID(idsel,func)	((idsel & 0x0F) << 4) | (func  & 0x07)
-#define ISERIES_ENCODE_DEVICE(agentid)	((0x10) | ((agentid&0x20)>>2) | (agentid&07))
+#define ISERIES_PCI_AGENTID(idsel, func)	\
+	(((idsel & 0x0F) << 4) | (func & 0x07))
+#define ISERIES_ENCODE_DEVICE(agentid)		\
+	((0x10) | ((agentid & 0x20) >> 2) | (agentid & 0x07))
 
-#define ISERIES_GET_DEVICE_FROM_SUBBUS(subbus)   ((subbus >> 5) & 0x7)
-#define ISERIES_GET_FUNCTION_FROM_SUBBUS(subbus) ((subbus >> 2) & 0x7)
+#define ISERIES_GET_DEVICE_FROM_SUBBUS(subbus)		((subbus >> 5) & 0x7)
+#define ISERIES_GET_FUNCTION_FROM_SUBBUS(subbus)	((subbus >> 2) & 0x7)
 
 /*
- * N.B. the ISERIES_DECODE_* macros are not used anywhere, and I think
- * the 0x71 (at least) must be wrong - 0x78 maybe?  -- paulus.
+ * Converts Virtual Address to Real Address for Hypervisor calls
  */
-#define ISERIES_DECODE_DEVFN(linuxdevfn)  (((linuxdevfn & 0x71) << 1) | (linuxdevfn & 0x07))
-#define ISERIES_DECODE_DEVICE(linuxdevfn) (((linuxdevfn & 0x38) >> 3) |(((linuxdevfn & 0x40) >> 2) + 0x10))
-#define ISERIES_DECODE_FUNCTION(linuxdevfn) (linuxdevfn & 0x07)
+#define ISERIES_HV_ADDR(virtaddr)	\
+	(0x8000000000000000 | virt_to_abs(virtaddr))
 
-/************************************************************************/
-/* Converts Virtual Address to Real Address for Hypervisor calls        */
-/************************************************************************/
-
-#define ISERIES_HV_ADDR(virtaddr)  (0x8000000000000000 | virt_to_abs(virtaddr))
-
-/************************************************************************/
-/* iSeries Device Information                                           */
-/************************************************************************/
-
+/*
+ * iSeries Device Information
+ */
 struct iSeries_Device_Node {
 	struct list_head Device_List;
-	struct pci_dev* PciDev;         /* Pointer to pci_dev structure*/
-        union HvDsaMap	DsaAddr;	/* Direct Select Address       */
-                                        /* busNumber,subBusNumber,     */ 
-	                                /* deviceId, barNumber         */
-	HvAgentId       AgentId;	/* Hypervisor DevFn            */
-	int             DevFn;          /* Linux devfn                 */
-	int             BarOffset;
-	int             Irq;            /* Assigned IRQ                */
-	int             ReturnCode;	/* Return Code Holder          */
-	int             IoRetry;        /* Current Retry Count         */
-	int             Flags;          /* Possible flags(disable/bist)*/
-	u16             Vendor;         /* Vendor ID                   */
-	u8              LogicalSlot;    /* Hv Slot Index for Tces      */
-	struct iommu_table* iommu_table;/* Device TCE Table            */ 
-	u8              PhbId;          /* Phb Card is on.             */
-	u16             Board;          /* Board Number                */
-	u8              FrameId;	/* iSeries spcn Frame Id       */
-	char            CardLocation[4];/* Char format of planar vpd   */
-	char            Location[20];   /* Frame  1, Card C10          */
+	struct pci_dev	*PciDev;
+	union HvDsaMap	DsaAddr;	/* Direct Select Address */
+					/* busNumber, subBusNumber, */
+					/* deviceId, barNumber */
+	int		DevFn;		/* Linux devfn */
+	int		Irq;		/* Assigned IRQ */
+	int		Flags;		/* Possible flags(disable/bist)*/
+	u8		LogicalSlot;	/* Hv Slot Index for Tces */
+	struct iommu_table *iommu_table;/* Device TCE Table */
 };
 
-/************************************************************************/
-/* Functions                                                            */
-/************************************************************************/
-
-extern int           iSeries_Device_Information(struct pci_dev*,char*, int);
-extern void          iSeries_Get_Location_Code(struct iSeries_Device_Node*);
-extern int           iSeries_Device_ToggleReset(struct pci_dev* PciDev, int AssertTime, int DelayTime);
+extern void	iSeries_Device_Information(struct pci_dev*, int);
 
 #endif /* _ISERIES_64_PCI_H */
diff --git a/include/asm-ppc64/iSeries/iSeries_proc.h b/include/asm-ppc64/iSeries/iSeries_proc.h
deleted file mode 100644
index adb6dc1..0000000
--- a/include/asm-ppc64/iSeries/iSeries_proc.h
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * iSeries_proc.h
- * Copyright (C) 2001  Kyle A. Lucke IBM Corporation
- * 
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- * 
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
- */
-#ifndef _ISERIES_PROC_H
-#define _ISERIES_PROC_H
-
-extern void iSeries_proc_early_init(void);
-
-#endif /* _iSeries_PROC_H */
diff --git a/include/asm-ppc64/iSeries/mf.h b/include/asm-ppc64/iSeries/mf.h
index db333e1..7e6a0d9 100644
--- a/include/asm-ppc64/iSeries/mf.h
+++ b/include/asm-ppc64/iSeries/mf.h
@@ -9,17 +9,16 @@
  * all partitions in the iSeries.  It also provides miscellaneous low-level
  * machine facility type operations.
  *
- * 
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
diff --git a/include/asm-ppc64/iSeries/vio.h b/include/asm-ppc64/iSeries/vio.h
index 3e5766a..6c05e62 100644
--- a/include/asm-ppc64/iSeries/vio.h
+++ b/include/asm-ppc64/iSeries/vio.h
@@ -8,32 +8,32 @@
  *           Colin Devilbiss <devilbis@us.ibm.com>
  *
  * (C) Copyright 2000 IBM Corporation
- * 
+ *
  * This header file is used by the iSeries virtual I/O device
  * drivers.  It defines the interfaces to the common functions
  * (implemented in drivers/char/viopath.h) as well as defining
- * common functions and structures.  Currently (at the time I 
+ * common functions and structures.  Currently (at the time I
  * wrote this comment) the iSeries virtual I/O device drivers
- * that use this are 
- *   drivers/block/viodasd.c 
+ * that use this are
+ *   drivers/block/viodasd.c
  *   drivers/char/viocons.c
  *   drivers/char/viotape.c
  *   drivers/cdrom/viocd.c
  *
  * The iSeries virtual ethernet support (veth.c) uses a whole
  * different set of functions.
- * 
+ *
  * This program is free software;  you can redistribute it and/or
  * modify it under the terms of the GNU General Public License as
  * published by the Free Software Foundation; either version 2 of the
  * License, or (at your option) anyu later version.
  *
  * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of 
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * General Public License for more details.  
+ * General Public License for more details.
  *
- * You should have received a copy of the GNU General Public License 
+ * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software Foundation,
  * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  *
@@ -44,39 +44,41 @@
 #include <asm/iSeries/HvTypes.h>
 #include <asm/iSeries/HvLpEvent.h>
 
-/* iSeries virtual I/O events use the subtype field in
+/*
+ * iSeries virtual I/O events use the subtype field in
  * HvLpEvent to figure out what kind of vio event is coming
  * in.  We use a table to route these, and this defines
  * the maximum number of distinct subtypes
  */
 #define VIO_MAX_SUBTYPES 8
 
-/* Each subtype can register a handler to process their events.
+/*
+ * Each subtype can register a handler to process their events.
  * The handler must have this interface.
  */
 typedef void (vio_event_handler_t) (struct HvLpEvent * event);
 
-int viopath_open(HvLpIndex remoteLp, int subtype, int numReq);
-int viopath_close(HvLpIndex remoteLp, int subtype, int numReq);
-int vio_setHandler(int subtype, vio_event_handler_t * beh);
-int vio_clearHandler(int subtype);
-int viopath_isactive(HvLpIndex lp);
-HvLpInstanceId viopath_sourceinst(HvLpIndex lp);
-HvLpInstanceId viopath_targetinst(HvLpIndex lp);
-void vio_set_hostlp(void);
-void *vio_get_event_buffer(int subtype);
-void vio_free_event_buffer(int subtype, void *buffer);
+extern int viopath_open(HvLpIndex remoteLp, int subtype, int numReq);
+extern int viopath_close(HvLpIndex remoteLp, int subtype, int numReq);
+extern int vio_setHandler(int subtype, vio_event_handler_t * beh);
+extern int vio_clearHandler(int subtype);
+extern int viopath_isactive(HvLpIndex lp);
+extern HvLpInstanceId viopath_sourceinst(HvLpIndex lp);
+extern HvLpInstanceId viopath_targetinst(HvLpIndex lp);
+extern void vio_set_hostlp(void);
+extern void *vio_get_event_buffer(int subtype);
+extern void vio_free_event_buffer(int subtype, void *buffer);
 
 extern HvLpIndex viopath_hostLp;
 extern HvLpIndex viopath_ourLp;
 
-#define VIOCHAR_MAX_DATA 200
+#define VIOCHAR_MAX_DATA	200
 
-#define VIOMAJOR_SUBTYPE_MASK 0xff00
-#define VIOMINOR_SUBTYPE_MASK 0x00ff
-#define VIOMAJOR_SUBTYPE_SHIFT 8
+#define VIOMAJOR_SUBTYPE_MASK	0xff00
+#define VIOMINOR_SUBTYPE_MASK	0x00ff
+#define VIOMAJOR_SUBTYPE_SHIFT	8
 
-#define VIOVERSION            0x0101
+#define VIOVERSION		0x0101
 
 /*
  * This is the general structure for VIO errors; each module should have
@@ -89,8 +91,8 @@
 	int errno;
 	const char *msg;
 };
-const struct vio_error_entry *vio_lookup_rc(const struct vio_error_entry
-					    *local_table, u16 rc);
+extern const struct vio_error_entry *vio_lookup_rc(
+		const struct vio_error_entry *local_table, u16 rc);
 
 enum viosubtypes {
 	viomajorsubtype_monitor = 0x0100,
@@ -102,7 +104,6 @@
 	viomajorsubtype_scsi = 0x0700
 };
 
-
 enum vioconfigsubtype {
 	vioconfigget = 0x0001,
 };
diff --git a/include/asm-ppc64/imalloc.h b/include/asm-ppc64/imalloc.h
index 3a45e91..e46ff68 100644
--- a/include/asm-ppc64/imalloc.h
+++ b/include/asm-ppc64/imalloc.h
@@ -4,9 +4,9 @@
 /*
  * Define the address range of the imalloc VM area.
  */
-#define PHBS_IO_BASE  	  IOREGIONBASE
-#define IMALLOC_BASE      (IOREGIONBASE + 0x80000000ul)	/* Reserve 2 gigs for PHBs */
-#define IMALLOC_END       (IOREGIONBASE + EADDR_MASK)
+#define PHBS_IO_BASE  	  VMALLOC_END
+#define IMALLOC_BASE      (PHBS_IO_BASE + 0x80000000ul)	/* Reserve 2 gigs for PHBs */
+#define IMALLOC_END       (VMALLOC_START + EADDR_MASK)
 
 
 /* imalloc region types */
@@ -18,7 +18,9 @@
 
 extern struct vm_struct * im_get_free_area(unsigned long size);
 extern struct vm_struct * im_get_area(unsigned long v_addr, unsigned long size,
-			int region_type);
-unsigned long im_free(void *addr);
+				      int region_type);
+extern void im_free(void *addr);
+
+extern unsigned long ioremap_bot;
 
 #endif /* _PPC64_IMALLOC_H */
diff --git a/include/asm-ppc64/iommu.h b/include/asm-ppc64/iommu.h
index bd53ca4..729de5c 100644
--- a/include/asm-ppc64/iommu.h
+++ b/include/asm-ppc64/iommu.h
@@ -82,24 +82,6 @@
 	unsigned long *it_map;       /* A simple allocation bitmap for now */
 };
 
-#ifdef CONFIG_PPC_ISERIES
-struct iommu_table_cb {
-	unsigned long	itc_busno;	/* Bus number for this tce table */
-	unsigned long	itc_start;	/* Will be NULL for secondary */
-	unsigned long	itc_totalsize;	/* Size (in pages) of whole table */
-	unsigned long	itc_offset;	/* Index into real tce table of the
-					   start of our section */
-	unsigned long	itc_size;	/* Size (in pages) of our section */
-	unsigned long	itc_index;	/* Index of this tce table */
-	unsigned short	itc_maxtables;	/* Max num of tables for partition */
-	unsigned char	itc_virtbus;	/* Flag to indicate virtual bus */
- 	unsigned char	itc_slotno;	/* IOA Tce Slot Index */
- 	unsigned char	itc_rsvd[4];
-};
-
-extern struct iommu_table vio_tce_table;      /* Tce table for virtual bus */
-#endif /* CONFIG_PPC_ISERIES */
-
 struct scatterlist;
 
 #ifdef CONFIG_PPC_MULTIPLATFORM
@@ -122,9 +104,6 @@
 
 #ifdef CONFIG_PPC_ISERIES
 
-/* Walks all buses and creates iommu tables */
-extern void iommu_setup_iSeries(void);
-
 /* Initializes tables for bio buses */
 extern void __init iommu_vio_init(void);
 
@@ -158,8 +137,12 @@
 extern void iommu_init_early_iSeries(void);
 extern void iommu_init_early_u3(void);
 
+#ifdef CONFIG_PCI
 extern void pci_iommu_init(void);
 extern void pci_direct_iommu_init(void);
+#else
+static inline void pci_iommu_init(void) { }
+#endif
 
 extern void alloc_u3_dart_table(void);
 
diff --git a/include/asm-ppc64/paca.h b/include/asm-ppc64/paca.h
index 1a0223b..ae76cae 100644
--- a/include/asm-ppc64/paca.h
+++ b/include/asm-ppc64/paca.h
@@ -20,13 +20,13 @@
 #include	<asm/types.h>
 #include	<asm/lppaca.h>
 #include	<asm/iSeries/ItLpRegSave.h>
+#include	<asm/iSeries/ItLpQueue.h>
 #include	<asm/mmu.h>
 
 register struct paca_struct *local_paca asm("r13");
 #define get_paca()	local_paca
 
 struct task_struct;
-struct ItLpQueue;
 
 /*
  * Defines the layout of the paca.
diff --git a/include/asm-ppc64/page.h b/include/asm-ppc64/page.h
index bcd2178..257d87e 100644
--- a/include/asm-ppc64/page.h
+++ b/include/asm-ppc64/page.h
@@ -202,9 +202,7 @@
 #define PAGE_OFFSET     ASM_CONST(0xC000000000000000)
 #define KERNELBASE      PAGE_OFFSET
 #define VMALLOCBASE     ASM_CONST(0xD000000000000000)
-#define IOREGIONBASE    ASM_CONST(0xE000000000000000)
 
-#define IO_REGION_ID       (IOREGIONBASE >> REGION_SHIFT)
 #define VMALLOC_REGION_ID  (VMALLOCBASE >> REGION_SHIFT)
 #define KERNEL_REGION_ID   (KERNELBASE >> REGION_SHIFT)
 #define USER_REGION_ID     (0UL)
diff --git a/include/asm-ppc64/pgtable.h b/include/asm-ppc64/pgtable.h
index 264c4f7..46cf61c 100644
--- a/include/asm-ppc64/pgtable.h
+++ b/include/asm-ppc64/pgtable.h
@@ -53,7 +53,8 @@
  * Define the address range of the vmalloc VM area.
  */
 #define VMALLOC_START (0xD000000000000000ul)
-#define VMALLOC_END   (VMALLOC_START + EADDR_MASK)
+#define VMALLOC_SIZE  (0x10000000000UL)
+#define VMALLOC_END   (VMALLOC_START + VMALLOC_SIZE)
 
 /*
  * Bits in a linux-style PTE.  These match the bits in the
@@ -239,9 +240,6 @@
 /* This now only contains the vmalloc pages */
 #define pgd_offset_k(address) pgd_offset(&init_mm, address)
 
-/* to find an entry in the ioremap page-table-directory */
-#define pgd_offset_i(address) (ioremap_pgd + pgd_index(address))
-
 /*
  * The following only work if pte_present() is true.
  * Undefined behaviour if not..
@@ -459,15 +457,12 @@
 #define __HAVE_ARCH_PTE_SAME
 #define pte_same(A,B)	(((pte_val(A) ^ pte_val(B)) & ~_PAGE_HPTEFLAGS) == 0)
 
-extern unsigned long ioremap_bot, ioremap_base;
-
 #define pmd_ERROR(e) \
 	printk("%s:%d: bad pmd %08x.\n", __FILE__, __LINE__, pmd_val(e))
 #define pgd_ERROR(e) \
 	printk("%s:%d: bad pgd %08x.\n", __FILE__, __LINE__, pgd_val(e))
 
 extern pgd_t swapper_pg_dir[];
-extern pgd_t ioremap_dir[];
 
 extern void paging_init(void);
 
diff --git a/include/asm-ppc64/processor.h b/include/asm-ppc64/processor.h
index 809c634b..3084099 100644
--- a/include/asm-ppc64/processor.h
+++ b/include/asm-ppc64/processor.h
@@ -430,16 +430,6 @@
 }
 
 /*
- * Note: the vm_start and vm_end fields here should *not*
- * be in kernel space.  (Could vm_end == vm_start perhaps?)
- */
-#define IOREMAP_MMAP { &ioremap_mm, 0, 0x1000, NULL, \
-		    PAGE_SHARED, VM_READ | VM_WRITE | VM_EXEC, \
-		    1, NULL, NULL }
-
-extern struct mm_struct ioremap_mm;
-
-/*
  * Return saved PC of a blocked thread. For now, this is the "user" PC
  */
 #define thread_saved_pc(tsk)    \
diff --git a/include/asm-ppc64/smp.h b/include/asm-ppc64/smp.h
index c8646fa..8115ecb 100644
--- a/include/asm-ppc64/smp.h
+++ b/include/asm-ppc64/smp.h
@@ -45,7 +45,7 @@
 void generic_mach_cpu_die(void);
 #endif
 
-#define __smp_processor_id() (get_paca()->paca_index)
+#define raw_smp_processor_id()	(get_paca()->paca_index)
 #define hard_smp_processor_id() (get_paca()->hw_cpu_id)
 
 extern cpumask_t cpu_sibling_map[NR_CPUS];
diff --git a/include/asm-s390/smp.h b/include/asm-s390/smp.h
index 9473786..dd50e57 100644
--- a/include/asm-s390/smp.h
+++ b/include/asm-s390/smp.h
@@ -47,7 +47,7 @@
  
 #define PROC_CHANGE_PENALTY	20		/* Schedule penalty */
 
-#define smp_processor_id() (S390_lowcore.cpu_data.cpu_nr)
+#define raw_smp_processor_id()	(S390_lowcore.cpu_data.cpu_nr)
 
 extern int smp_get_cpu(cpumask_t cpu_map);
 extern void smp_put_cpu(int cpu);
diff --git a/include/asm-sh/page.h b/include/asm-sh/page.h
index 4c6d129..180467b 100644
--- a/include/asm-sh/page.h
+++ b/include/asm-sh/page.h
@@ -31,6 +31,7 @@
 #define HPAGE_SIZE		(1UL << HPAGE_SHIFT)
 #define HPAGE_MASK		(~(HPAGE_SIZE-1))
 #define HUGETLB_PAGE_ORDER	(HPAGE_SHIFT-PAGE_SHIFT)
+#define ARCH_HAS_SETCLEAR_HUGE_PTE
 #endif
 
 #ifdef __KERNEL__
diff --git a/include/asm-sh/pgtable.h b/include/asm-sh/pgtable.h
index cd847a4..ecb9095 100644
--- a/include/asm-sh/pgtable.h
+++ b/include/asm-sh/pgtable.h
@@ -196,6 +196,7 @@
 static inline pte_t pte_mkdirty(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_DIRTY)); return pte; }
 static inline pte_t pte_mkyoung(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_ACCESSED)); return pte; }
 static inline pte_t pte_mkwrite(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_RW)); return pte; }
+static inline pte_t pte_mkhuge(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_SZHUGE)); return pte; }
 
 /*
  * Macro and implementation to make a page protection as uncachable.
diff --git a/include/asm-sh/smp.h b/include/asm-sh/smp.h
index 38b5446..f19a8b3 100644
--- a/include/asm-sh/smp.h
+++ b/include/asm-sh/smp.h
@@ -25,7 +25,7 @@
 
 #define cpu_online(cpu)		cpu_isset(cpu, cpu_online_map)
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id()	(current_thread_info()->cpu)
 
 /* I've no idea what the real meaning of this is */
 #define PROC_CHANGE_PENALTY	20
diff --git a/include/asm-sh64/page.h b/include/asm-sh64/page.h
index e1f7f5a..d6167f1 100644
--- a/include/asm-sh64/page.h
+++ b/include/asm-sh64/page.h
@@ -41,6 +41,7 @@
 #define HPAGE_SIZE		(1UL << HPAGE_SHIFT)
 #define HPAGE_MASK		(~(HPAGE_SIZE-1))
 #define HUGETLB_PAGE_ORDER	(HPAGE_SHIFT-PAGE_SHIFT)
+#define ARCH_HAS_SETCLEAR_HUGE_PTE
 #endif
 
 #ifdef __KERNEL__
diff --git a/include/asm-sh64/pgtable.h b/include/asm-sh64/pgtable.h
index 525e152..78ac6be 100644
--- a/include/asm-sh64/pgtable.h
+++ b/include/asm-sh64/pgtable.h
@@ -430,6 +430,8 @@
 extern inline pte_t pte_mkexec(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_EXECUTE)); return pte; }
 extern inline pte_t pte_mkdirty(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_DIRTY)); return pte; }
 extern inline pte_t pte_mkyoung(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_ACCESSED)); return pte; }
+extern inline pte_t pte_mkhuge(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_SZHUGE)); return pte; }
+
 
 /*
  * Conversion functions: convert a page and protection to a page entry.
diff --git a/include/asm-sparc/smp.h b/include/asm-sparc/smp.h
index f986c0d..4f96d83 100644
--- a/include/asm-sparc/smp.h
+++ b/include/asm-sparc/smp.h
@@ -148,7 +148,7 @@
 }
 #endif
 
-#define smp_processor_id()	(current_thread_info()->cpu)
+#define raw_smp_processor_id()		(current_thread_info()->cpu)
 
 #define prof_multiplier(__cpu)		cpu_data(__cpu).multiplier
 #define prof_counter(__cpu)		cpu_data(__cpu).counter
diff --git a/include/asm-sparc64/page.h b/include/asm-sparc64/page.h
index 219ea04..b87dbbd 100644
--- a/include/asm-sparc64/page.h
+++ b/include/asm-sparc64/page.h
@@ -95,6 +95,8 @@
 #define HPAGE_SIZE		(_AC(1,UL) << HPAGE_SHIFT)
 #define HPAGE_MASK		(~(HPAGE_SIZE - 1UL))
 #define HUGETLB_PAGE_ORDER	(HPAGE_SHIFT - PAGE_SHIFT)
+#define ARCH_HAS_SETCLEAR_HUGE_PTE
+#define ARCH_HAS_HUGETLB_PREFAULT_HOOK
 #endif
 
 #define TASK_UNMAPPED_BASE	(test_thread_flag(TIF_32BIT) ? \
diff --git a/include/asm-sparc64/pgtable.h b/include/asm-sparc64/pgtable.h
index ae2cd5b..1ae00c5 100644
--- a/include/asm-sparc64/pgtable.h
+++ b/include/asm-sparc64/pgtable.h
@@ -286,6 +286,7 @@
 #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_ACCESSED | _PAGE_R))
 #define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_WRITE))
 #define pte_mkdirty(pte)	(__pte(pte_val(pte) | _PAGE_MODIFIED | _PAGE_W))
+#define pte_mkhuge(pte)		(__pte(pte_val(pte) | _PAGE_SZHUGE))
 
 /* to find an entry in a page-table-directory. */
 #define pgd_index(address)	(((address) >> PGDIR_SHIFT) & (PTRS_PER_PGD - 1))
diff --git a/include/asm-sparc64/processor.h b/include/asm-sparc64/processor.h
index bc1445b..d0bee24 100644
--- a/include/asm-sparc64/processor.h
+++ b/include/asm-sparc64/processor.h
@@ -192,6 +192,40 @@
 
 #define cpu_relax()	barrier()
 
+/* Prefetch support.  This is tuned for UltraSPARC-III and later.
+ * UltraSPARC-I will treat these as nops, and UltraSPARC-II has
+ * a shallower prefetch queue than later chips.
+ */
+#define ARCH_HAS_PREFETCH
+#define ARCH_HAS_PREFETCHW
+#define ARCH_HAS_SPINLOCK_PREFETCH
+
+static inline void prefetch(const void *x)
+{
+	/* We do not use the read prefetch mnemonic because that
+	 * prefetches into the prefetch-cache which only is accessible
+	 * by floating point operations in UltraSPARC-III and later.
+	 * By contrast, "#one_write" prefetches into the L2 cache
+	 * in shared state.
+	 */
+	__asm__ __volatile__("prefetch [%0], #one_write"
+			     : /* no outputs */
+			     : "r" (x));
+}
+
+static inline void prefetchw(const void *x)
+{
+	/* The most optimal prefetch to use for writes is
+	 * "#n_writes".  This brings the cacheline into the
+	 * L2 cache in "owned" state.
+	 */
+	__asm__ __volatile__("prefetch [%0], #n_writes"
+			     : /* no outputs */
+			     : "r" (x));
+}
+
+#define spin_lock_prefetch(x)	prefetchw(x)
+
 #endif /* !(__ASSEMBLY__) */
 
 #endif /* !(__ASM_SPARC64_PROCESSOR_H) */
diff --git a/include/asm-sparc64/smp.h b/include/asm-sparc64/smp.h
index 5e3e06d..110a2de 100644
--- a/include/asm-sparc64/smp.h
+++ b/include/asm-sparc64/smp.h
@@ -64,7 +64,7 @@
 	}
 }
 
-#define smp_processor_id() (current_thread_info()->cpu)
+#define raw_smp_processor_id() (current_thread_info()->cpu)
 
 #endif /* !(__ASSEMBLY__) */
 
diff --git a/include/asm-um/smp.h b/include/asm-um/smp.h
index 4412d5d..d879eba 100644
--- a/include/asm-um/smp.h
+++ b/include/asm-um/smp.h
@@ -8,7 +8,8 @@
 #include "asm/current.h"
 #include "linux/cpumask.h"
 
-#define smp_processor_id() (current_thread->cpu)
+#define raw_smp_processor_id() (current_thread->cpu)
+
 #define cpu_logical_map(n) (n)
 #define cpu_number_map(n) (n)
 #define PROC_CHANGE_PENALTY	15 /* Pick a number, any number */
diff --git a/include/asm-x86_64/a.out.h b/include/asm-x86_64/a.out.h
index 5952914..7255cde 100644
--- a/include/asm-x86_64/a.out.h
+++ b/include/asm-x86_64/a.out.h
@@ -21,7 +21,7 @@
 
 #ifdef __KERNEL__
 #include <linux/thread_info.h>
-#define STACK_TOP (test_thread_flag(TIF_IA32) ? IA32_PAGE_OFFSET : TASK_SIZE)
+#define STACK_TOP TASK_SIZE
 #endif
 
 #endif /* __A_OUT_GNU_H__ */
diff --git a/include/asm-x86_64/page.h b/include/asm-x86_64/page.h
index f430480..9ce338c3a 100644
--- a/include/asm-x86_64/page.h
+++ b/include/asm-x86_64/page.h
@@ -28,6 +28,7 @@
 #define HPAGE_SIZE	((1UL) << HPAGE_SHIFT)
 #define HPAGE_MASK	(~(HPAGE_SIZE - 1))
 #define HUGETLB_PAGE_ORDER	(HPAGE_SHIFT - PAGE_SHIFT)
+#define ARCH_HAS_HUGETLB_CLEAN_STALE_PGTABLE
 
 #ifdef __KERNEL__
 #ifndef __ASSEMBLY__
diff --git a/include/asm-x86_64/pgtable.h b/include/asm-x86_64/pgtable.h
index db2a0ef..4eec176 100644
--- a/include/asm-x86_64/pgtable.h
+++ b/include/asm-x86_64/pgtable.h
@@ -253,6 +253,7 @@
 extern inline int pte_write(pte_t pte)		{ return pte_val(pte) & _PAGE_RW; }
 static inline int pte_file(pte_t pte)		{ return pte_val(pte) & _PAGE_FILE; }
 
+#define __LARGE_PTE (_PAGE_PSE|_PAGE_PRESENT)
 extern inline pte_t pte_rdprotect(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) & ~_PAGE_USER)); return pte; }
 extern inline pte_t pte_exprotect(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) & ~_PAGE_USER)); return pte; }
 extern inline pte_t pte_mkclean(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) & ~_PAGE_DIRTY)); return pte; }
@@ -263,6 +264,7 @@
 extern inline pte_t pte_mkdirty(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_DIRTY)); return pte; }
 extern inline pte_t pte_mkyoung(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_ACCESSED)); return pte; }
 extern inline pte_t pte_mkwrite(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | _PAGE_RW)); return pte; }
+extern inline pte_t pte_mkhuge(pte_t pte)	{ set_pte(&pte, __pte(pte_val(pte) | __LARGE_PTE)); return pte; }
 
 struct vm_area_struct;
 
@@ -290,7 +292,6 @@
  */
 #define pgprot_noncached(prot)	(__pgprot(pgprot_val(prot) | _PAGE_PCD | _PAGE_PWT))
 
-#define __LARGE_PTE (_PAGE_PSE|_PAGE_PRESENT) 
 static inline int pmd_large(pmd_t pte) { 
 	return (pmd_val(pte) & __LARGE_PTE) == __LARGE_PTE; 
 } 	
diff --git a/include/asm-x86_64/processor.h b/include/asm-x86_64/processor.h
index d641b19..8b55f13 100644
--- a/include/asm-x86_64/processor.h
+++ b/include/asm-x86_64/processor.h
@@ -160,16 +160,17 @@
 /*
  * User space process size. 47bits minus one guard page.
  */
-#define TASK_SIZE	(0x800000000000UL - 4096)
+#define TASK_SIZE64	(0x800000000000UL - 4096)
 
 /* This decides where the kernel will search for a free chunk of vm
  * space during mmap's.
  */
 #define IA32_PAGE_OFFSET ((current->personality & ADDR_LIMIT_3GB) ? 0xc0000000 : 0xFFFFe000)
-#define TASK_UNMAPPED_32 PAGE_ALIGN(IA32_PAGE_OFFSET/3)
-#define TASK_UNMAPPED_64 PAGE_ALIGN(TASK_SIZE/3) 
-#define TASK_UNMAPPED_BASE	\
-	(test_thread_flag(TIF_IA32) ? TASK_UNMAPPED_32 : TASK_UNMAPPED_64)  
+
+#define TASK_SIZE 		(test_thread_flag(TIF_IA32) ? IA32_PAGE_OFFSET : TASK_SIZE64)
+#define TASK_SIZE_OF(child) 	((test_tsk_thread_flag(child, TIF_IA32)) ? IA32_PAGE_OFFSET : TASK_SIZE64)
+
+#define TASK_UNMAPPED_BASE	PAGE_ALIGN(TASK_SIZE/3)
 
 /*
  * Size of io_bitmap.
diff --git a/include/asm-x86_64/smp.h b/include/asm-x86_64/smp.h
index 96844fe..a7425aa 100644
--- a/include/asm-x86_64/smp.h
+++ b/include/asm-x86_64/smp.h
@@ -68,7 +68,7 @@
 	return cpus_weight(cpu_callout_map);
 }
 
-#define __smp_processor_id() read_pda(cpunumber)
+#define raw_smp_processor_id() read_pda(cpunumber)
 
 extern __inline int hard_smp_processor_id(void)
 {
diff --git a/include/linux/arcfb.h b/include/linux/arcfb.h
new file mode 100644
index 0000000..721e765
--- /dev/null
+++ b/include/linux/arcfb.h
@@ -0,0 +1,8 @@
+#ifndef __LINUX_ARCFB_H__
+#define __LINUX_ARCFB_H__
+
+#define FBIO_WAITEVENT		_IO('F', 0x88)
+#define FBIO_GETCONTROL2	_IOR('F', 0x89, size_t)
+
+#endif
+
diff --git a/include/linux/auto_fs4.h b/include/linux/auto_fs4.h
index a1657fb..9343c89 100644
--- a/include/linux/auto_fs4.h
+++ b/include/linux/auto_fs4.h
@@ -23,7 +23,7 @@
 #define AUTOFS_MIN_PROTO_VERSION	3
 #define AUTOFS_MAX_PROTO_VERSION	4
 
-#define AUTOFS_PROTO_SUBVERSION		6
+#define AUTOFS_PROTO_SUBVERSION		7
 
 /* Mask for expire behaviour */
 #define AUTOFS_EXP_IMMEDIATE		1
diff --git a/include/linux/fb.h b/include/linux/fb.h
index b468bf4..bc24bee 100644
--- a/include/linux/fb.h
+++ b/include/linux/fb.h
@@ -524,11 +524,11 @@
 	u32 offset;		/* current offset to buffer		*/
 	u32 buf_align;		/* byte alignment of each bitmap	*/
 	u32 scan_align;		/* alignment per scanline		*/
-	u32 access_align;	/* alignment per read/write		*/
+	u32 access_align;	/* alignment per read/write (bits)	*/
 	u32 flags;		/* see FB_PIXMAP_*			*/
 	/* access methods */
-	void (*outbuf)(struct fb_info *info, u8 *addr, u8 *src, unsigned int size);
-	u8   (*inbuf) (struct fb_info *info, u8 *addr);
+	void (*writeio)(struct fb_info *info, void __iomem *dst, void *src, unsigned int size);
+	void (*readio) (struct fb_info *info, void *dst, void __iomem *src, unsigned int size);
 };
 
 
@@ -816,18 +816,9 @@
 extern int fb_prepare_logo(struct fb_info *fb_info);
 extern int fb_show_logo(struct fb_info *fb_info);
 extern char* fb_get_buffer_offset(struct fb_info *info, struct fb_pixmap *buf, u32 size);
-extern void fb_iomove_buf_unaligned(struct fb_info *info, struct fb_pixmap *buf,
-				u8 *dst, u32 d_pitch, u8 *src, u32 idx,
+extern void fb_pad_unaligned_buffer(u8 *dst, u32 d_pitch, u8 *src, u32 idx,
 				u32 height, u32 shift_high, u32 shift_low, u32 mod);
-extern void fb_iomove_buf_aligned(struct fb_info *info, struct fb_pixmap *buf,
-				u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch,
-				u32 height);
-extern void fb_sysmove_buf_unaligned(struct fb_info *info, struct fb_pixmap *buf,
-				u8 *dst, u32 d_pitch, u8 *src, u32 idx,
-				u32 height, u32 shift_high, u32 shift_low, u32 mod);
-extern void fb_sysmove_buf_aligned(struct fb_info *info, struct fb_pixmap *buf,
-				u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch,
-				u32 height);
+extern void fb_pad_aligned_buffer(u8 *dst, u32 d_pitch, u8 *src, u32 s_pitch, u32 height);
 extern void fb_set_suspend(struct fb_info *info, int state);
 extern int fb_get_color_depth(struct fb_var_screeninfo *var);
 extern int fb_get_options(char *name, char **option);
diff --git a/include/linux/font.h b/include/linux/font.h
index fc2d690..8fc80a7 100644
--- a/include/linux/font.h
+++ b/include/linux/font.h
@@ -25,19 +25,23 @@
 #define VGA8x16_IDX	1
 #define PEARL8x8_IDX	2
 #define VGA6x11_IDX	3
-#define SUN8x16_IDX	4
-#define SUN12x22_IDX	5
-#define ACORN8x8_IDX	6
-#define	MINI4x6_IDX	7
+#define FONT7x14_IDX	4
+#define	FONT10x18_IDX	5
+#define SUN8x16_IDX	6
+#define SUN12x22_IDX	7
+#define ACORN8x8_IDX	8
+#define	MINI4x6_IDX	9
 
 extern struct font_desc	font_vga_8x8,
-				font_vga_8x16,
-				font_pearl_8x8,
-				font_vga_6x11,
-				font_sun_8x16,
-				font_sun_12x22,
-				font_acorn_8x8,
-				font_mini_4x6;
+			font_vga_8x16,
+			font_pearl_8x8,
+			font_vga_6x11,
+			font_7x14,
+			font_10x18,
+			font_sun_8x16,
+			font_sun_12x22,
+			font_acorn_8x8,
+			font_mini_4x6;
 
 /* Find a font with a specific name */
 
diff --git a/include/linux/fsl_devices.h b/include/linux/fsl_devices.h
index faaff4c..70f54af 100644
--- a/include/linux/fsl_devices.h
+++ b/include/linux/fsl_devices.h
@@ -51,6 +51,7 @@
 
 	/* board specific information */
 	u32 board_flags;
+	u32 phy_flags;
 	u32 phyid;
 	u32 interruptPHY;
 	u8 mac_addr[6];
@@ -61,9 +62,14 @@
 #define FSL_GIANFAR_DEV_HAS_COALESCE		0x00000002
 #define FSL_GIANFAR_DEV_HAS_RMON		0x00000004
 #define FSL_GIANFAR_DEV_HAS_MULTI_INTR		0x00000008
+#define FSL_GIANFAR_DEV_HAS_CSUM		0x00000010
+#define FSL_GIANFAR_DEV_HAS_VLAN		0x00000020
+#define FSL_GIANFAR_DEV_HAS_EXTENDED_HASH	0x00000040
+#define FSL_GIANFAR_DEV_HAS_PADDING		0x00000080
 
 /* Flags in gianfar_platform_data */
-#define FSL_GIANFAR_BRD_HAS_PHY_INTR	0x00000001	/* if not set use a timer */
+#define FSL_GIANFAR_BRD_HAS_PHY_INTR	0x00000001 /* set or use a timer */
+#define FSL_GIANFAR_BRD_IS_REDUCED	0x00000002 /* Set if RGMII, RMII */
 
 struct fsl_i2c_platform_data {
 	/* device specific information */
diff --git a/include/linux/genalloc.h b/include/linux/genalloc.h
new file mode 100644
index 0000000..7fd0576
--- /dev/null
+++ b/include/linux/genalloc.h
@@ -0,0 +1,40 @@
+/*
+ * Basic general purpose allocator for managing special purpose memory
+ * not managed by the regular kmalloc/kfree interface.
+ * Uses for this includes on-device special memory, uncached memory
+ * etc.
+ *
+ * This code is based on the buddy allocator found in the sym53c8xx_2
+ * driver, adapted for general purpose use.
+ *
+ * This source code is licensed under the GNU General Public License,
+ * Version 2.  See the file COPYING for more details.
+ */
+
+#include <linux/spinlock.h>
+
+#define ALLOC_MIN_SHIFT		5 /* 32 bytes minimum */
+/*
+ *  Link between free memory chunks of a given size.
+ */
+struct gen_pool_link {
+	struct gen_pool_link *next;
+};
+
+/*
+ *  Memory pool descriptor.
+ */
+struct gen_pool {
+	spinlock_t lock;
+	unsigned long (*get_new_chunk)(struct gen_pool *);
+	struct gen_pool *next;
+	struct gen_pool_link *h;
+	unsigned long private;
+	int max_chunk_shift;
+};
+
+unsigned long gen_pool_alloc(struct gen_pool *poolp, int size);
+void gen_pool_free(struct gen_pool *mp, unsigned long ptr, int size);
+struct gen_pool *gen_pool_create(int nr_chunks, int max_chunk_shift,
+				 unsigned long (*fp)(struct gen_pool *),
+				 unsigned long data);
diff --git a/include/linux/gfp.h b/include/linux/gfp.h
index af7407e..8d6bf60 100644
--- a/include/linux/gfp.h
+++ b/include/linux/gfp.h
@@ -39,6 +39,7 @@
 #define __GFP_COMP	0x4000u	/* Add compound page metadata */
 #define __GFP_ZERO	0x8000u	/* Return zeroed page on success */
 #define __GFP_NOMEMALLOC 0x10000u /* Don't use emergency reserves */
+#define __GFP_NORECLAIM  0x20000u /* No realy zone reclaim during allocation */
 
 #define __GFP_BITS_SHIFT 20	/* Room for 20 __GFP_FOO bits */
 #define __GFP_BITS_MASK ((1 << __GFP_BITS_SHIFT) - 1)
@@ -47,7 +48,7 @@
 #define GFP_LEVEL_MASK (__GFP_WAIT|__GFP_HIGH|__GFP_IO|__GFP_FS| \
 			__GFP_COLD|__GFP_NOWARN|__GFP_REPEAT| \
 			__GFP_NOFAIL|__GFP_NORETRY|__GFP_NO_GROW|__GFP_COMP| \
-			__GFP_NOMEMALLOC)
+			__GFP_NOMEMALLOC|__GFP_NORECLAIM)
 
 #define GFP_ATOMIC	(__GFP_HIGH)
 #define GFP_NOIO	(__GFP_WAIT)
@@ -132,5 +133,10 @@
 #define free_page(addr) free_pages((addr),0)
 
 void page_alloc_init(void);
+#ifdef CONFIG_NUMA
+void drain_remote_pages(void);
+#else
+static inline void drain_remote_pages(void) { };
+#endif
 
 #endif /* __LINUX_GFP_H */
diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
index 6af1ae4..f529d14 100644
--- a/include/linux/hugetlb.h
+++ b/include/linux/hugetlb.h
@@ -4,6 +4,7 @@
 #ifdef CONFIG_HUGETLB_PAGE
 
 #include <linux/mempolicy.h>
+#include <asm/tlbflush.h>
 
 struct ctl_table;
 
@@ -22,12 +23,6 @@
 int hugetlb_report_node_meminfo(int, char *);
 int is_hugepage_mem_enough(size_t);
 unsigned long hugetlb_total_pages(void);
-struct page *follow_huge_addr(struct mm_struct *mm, unsigned long address,
-			      int write);
-struct page *follow_huge_pmd(struct mm_struct *mm, unsigned long address,
-				pmd_t *pmd, int write);
-int is_aligned_hugepage_range(unsigned long addr, unsigned long len);
-int pmd_huge(pmd_t pmd);
 struct page *alloc_huge_page(void);
 void free_huge_page(struct page *);
 
@@ -35,6 +30,17 @@
 extern const unsigned long hugetlb_zero, hugetlb_infinity;
 extern int sysctl_hugetlb_shm_group;
 
+/* arch callbacks */
+
+pte_t *huge_pte_alloc(struct mm_struct *mm, unsigned long addr);
+pte_t *huge_pte_offset(struct mm_struct *mm, unsigned long addr);
+struct page *follow_huge_addr(struct mm_struct *mm, unsigned long address,
+			      int write);
+struct page *follow_huge_pmd(struct mm_struct *mm, unsigned long address,
+				pmd_t *pmd, int write);
+int is_aligned_hugepage_range(unsigned long addr, unsigned long len);
+int pmd_huge(pmd_t pmd);
+
 #ifndef ARCH_HAS_HUGEPAGE_ONLY_RANGE
 #define is_hugepage_only_range(mm, addr, len)	0
 #define hugetlb_free_pgd_range(tlb, addr, end, floor, ceiling) \
@@ -48,6 +54,28 @@
 int prepare_hugepage_range(unsigned long addr, unsigned long len);
 #endif
 
+#ifndef ARCH_HAS_SETCLEAR_HUGE_PTE
+#define set_huge_pte_at(mm, addr, ptep, pte)	set_pte_at(mm, addr, ptep, pte)
+#define huge_ptep_get_and_clear(mm, addr, ptep) ptep_get_and_clear(mm, addr, ptep)
+#else
+void set_huge_pte_at(struct mm_struct *mm, unsigned long addr,
+		     pte_t *ptep, pte_t pte);
+pte_t huge_ptep_get_and_clear(struct mm_struct *mm, unsigned long addr,
+			      pte_t *ptep);
+#endif
+
+#ifndef ARCH_HAS_HUGETLB_PREFAULT_HOOK
+#define hugetlb_prefault_arch_hook(mm)		do { } while (0)
+#else
+void hugetlb_prefault_arch_hook(struct mm_struct *mm);
+#endif
+
+#ifndef ARCH_HAS_HUGETLB_CLEAN_STALE_PGTABLE
+#define hugetlb_clean_stale_pgtable(pte)	BUG()
+#else
+void hugetlb_clean_stale_pgtable(pte_t *pte);
+#endif
+
 #else /* !CONFIG_HUGETLB_PAGE */
 
 static inline int is_vm_hugetlb_page(struct vm_area_struct *vma)
diff --git a/include/linux/ioc4.h b/include/linux/ioc4.h
new file mode 100644
index 0000000..3dd18b7
--- /dev/null
+++ b/include/linux/ioc4.h
@@ -0,0 +1,179 @@
+/*
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * Copyright (c) 2005 Silicon Graphics, Inc.  All Rights Reserved.
+ */
+
+#ifndef _LINUX_IOC4_H
+#define _LINUX_IOC4_H
+
+#include <linux/interrupt.h>
+
+/***************
+ * Definitions *
+ ***************/
+
+/* Miscellaneous values inherent to hardware */
+
+#define IOC4_EXTINT_COUNT_DIVISOR 520	/* PCI clocks per COUNT tick */
+
+/***********************************
+ * Structures needed by subdrivers *
+ ***********************************/
+
+/* This structure fully describes the IOC4 miscellaneous registers which
+ * appear at bar[0]+0x00000 through bar[0]+0x0005c.  The corresponding
+ * PCI resource is managed by the main IOC4 driver because it contains
+ * registers of interest to many different IOC4 subdrivers.
+ */
+struct ioc4_misc_regs {
+	/* Miscellaneous IOC4 registers */
+	union ioc4_pci_err_addr_l {
+		uint32_t raw;
+		struct {
+			uint32_t valid:1;	/* Address captured */
+			uint32_t master_id:4;	/* Unit causing error
+						 * 0/1: Serial port 0 TX/RX
+						 * 2/3: Serial port 1 TX/RX
+						 * 4/5: Serial port 2 TX/RX
+						 * 6/7: Serial port 3 TX/RX
+						 * 8: ATA/ATAPI
+						 * 9-15: Undefined
+						 */
+			uint32_t mul_err:1;	/* Multiple errors occurred */
+			uint32_t addr:26;	/* Bits 31-6 of error addr */
+		} fields;
+	} pci_err_addr_l;
+	uint32_t pci_err_addr_h;	/* Bits 63-32 of error addr */
+	union ioc4_sio_int {
+		uint32_t raw;
+		struct {
+			uint8_t tx_mt:1;	/* TX ring buffer empty */
+			uint8_t rx_full:1;	/* RX ring buffer full */
+			uint8_t rx_high:1;	/* RX high-water exceeded */
+			uint8_t rx_timer:1;	/* RX timer has triggered */
+			uint8_t delta_dcd:1;	/* DELTA_DCD seen */
+			uint8_t delta_cts:1;	/* DELTA_CTS seen */
+			uint8_t intr_pass:1;	/* Interrupt pass-through */
+			uint8_t tx_explicit:1;	/* TX, MCW, or delay complete */
+		} fields[4];
+	} sio_ir;		/* Serial interrupt state */
+	union ioc4_other_int {
+		uint32_t raw;
+		struct {
+			uint32_t ata_int:1;	/* ATA port passthru */
+			uint32_t ata_memerr:1;	/* ATA halted by mem error */
+			uint32_t memerr:4;	/* Serial halted by mem err */
+			uint32_t kbd_int:1;	/* kbd/mouse intr asserted */
+			uint32_t reserved:16;	/* zero */
+			uint32_t rt_int:1;	/* INT_OUT section latch */
+			uint32_t gen_int:8;	/* Intr. from generic pins */
+		} fields;
+	} other_ir;		/* Other interrupt state */
+	union ioc4_sio_int sio_ies;	/* Serial interrupt enable set */
+	union ioc4_other_int other_ies;	/* Other interrupt enable set */
+	union ioc4_sio_int sio_iec;	/* Serial interrupt enable clear */
+	union ioc4_other_int other_iec;	/* Other interrupt enable clear */
+	union ioc4_sio_cr {
+		uint32_t raw;
+		struct {
+			uint32_t cmd_pulse:4;	/* Bytebus strobe width */
+			uint32_t arb_diag:3;	/* PCI bus requester */
+			uint32_t sio_diag_idle:1;	/* Active ser req? */
+			uint32_t ata_diag_idle:1;	/* Active ATA req? */
+			uint32_t ata_diag_active:1;	/* ATA req is winner */
+			uint32_t reserved:22;	/* zero */
+		} fields;
+	} sio_cr;
+	uint32_t unused1;
+	union ioc4_int_out {
+		uint32_t raw;
+		struct {
+			uint32_t count:16;	/* Period control */
+			uint32_t mode:3;	/* Output signal shape */
+			uint32_t reserved:11;	/* zero */
+			uint32_t diag:1;	/* Timebase control */
+			uint32_t int_out:1;	/* Current value */
+		} fields;
+	} int_out;		/* External interrupt output control */
+	uint32_t unused2;
+	union ioc4_gpcr {
+		uint32_t raw;
+		struct {
+			uint32_t dir:8;	/* Pin direction */
+			uint32_t edge:8;	/* Edge/level mode */
+			uint32_t reserved1:4;	/* zero */
+			uint32_t int_out_en:1;	/* INT_OUT enable */
+			uint32_t reserved2:11;	/* zero */
+		} fields;
+	} gpcr_s;		/* Generic PIO control set */
+	union ioc4_gpcr gpcr_c;	/* Generic PIO control clear */
+	union ioc4_gpdr {
+		uint32_t raw;
+		struct {
+			uint32_t gen_pin:8;	/* State of pins */
+			uint32_t reserved:24;
+		} fields;
+	} gpdr;			/* Generic PIO data */
+	uint32_t unused3;
+	union ioc4_gppr {
+		uint32_t raw;
+		struct {
+			uint32_t gen_pin:1;	/* Single pin state */
+			uint32_t reserved:31;
+		} fields;
+	} gppr[8];		/* Generic PIO pins */
+};
+
+/* Masks for GPCR DIR pins */
+#define IOC4_GPCR_DIR_0 0x01	/* External interrupt output */
+#define IOC4_GPCR_DIR_1 0x02	/* External interrupt input */
+#define IOC4_GPCR_DIR_2 0x04
+#define IOC4_GPCR_DIR_3 0x08	/* Keyboard/mouse presence */
+#define IOC4_GPCR_DIR_4 0x10	/* Ser. port 0 xcvr select (0=232, 1=422) */
+#define IOC4_GPCR_DIR_5 0x20	/* Ser. port 1 xcvr select (0=232, 1=422) */
+#define IOC4_GPCR_DIR_6 0x40	/* Ser. port 2 xcvr select (0=232, 1=422) */
+#define IOC4_GPCR_DIR_7 0x80	/* Ser. port 3 xcvr select (0=232, 1=422) */
+
+/* Masks for GPCR EDGE pins */
+#define IOC4_GPCR_EDGE_0 0x01
+#define IOC4_GPCR_EDGE_1 0x02	/* External interrupt input */
+#define IOC4_GPCR_EDGE_2 0x04
+#define IOC4_GPCR_EDGE_3 0x08
+#define IOC4_GPCR_EDGE_4 0x10
+#define IOC4_GPCR_EDGE_5 0x20
+#define IOC4_GPCR_EDGE_6 0x40
+#define IOC4_GPCR_EDGE_7 0x80
+
+/* One of these per IOC4 */
+struct ioc4_driver_data {
+	struct list_head idd_list;
+	unsigned long idd_bar0;
+	struct pci_dev *idd_pdev;
+	const struct pci_device_id *idd_pci_id;
+	struct __iomem ioc4_misc_regs *idd_misc_regs;
+	unsigned long count_period;
+	void *idd_serial_data;
+};
+
+/* One per submodule */
+struct ioc4_submodule {
+	struct list_head is_list;
+	char *is_name;
+	struct module *is_owner;
+	int (*is_probe) (struct ioc4_driver_data *);
+	int (*is_remove) (struct ioc4_driver_data *);
+};
+
+#define IOC4_NUM_CARDS		8	/* max cards per partition */
+
+/**********************************
+ * Functions needed by submodules *
+ **********************************/
+
+extern int ioc4_register_submodule(struct ioc4_submodule *);
+extern void ioc4_unregister_submodule(struct ioc4_submodule *);
+
+#endif				/* _LINUX_IOC4_H */
diff --git a/include/linux/ioc4_common.h b/include/linux/ioc4_common.h
deleted file mode 100644
index b03bcc4..0000000
--- a/include/linux/ioc4_common.h
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * This file is subject to the terms and conditions of the GNU General Public
- * License.  See the file "COPYING" in the main directory of this archive
- * for more details.
- *
- * Copyright (c) 2005 Silicon Graphics, Inc.  All Rights Reserved.
- */
-
-#ifndef _LINUX_IOC4_COMMON_H
-#define _LINUX_IOC4_COMMON_H
-
-/* prototypes */
-
-int ioc4_serial_init(void);
-
-int ioc4_serial_attach_one(struct pci_dev *pdev, const struct
-				pci_device_id *pci_id);
-int ioc4_ide_attach_one(struct pci_dev *pdev, const struct
-				pci_device_id *pci_id);
-
-#endif	/* _LINUX_IOC4_COMMON_H */
diff --git a/include/linux/irq.h b/include/linux/irq.h
index c3ff4d1..7fc1022 100644
--- a/include/linux/irq.h
+++ b/include/linux/irq.h
@@ -47,6 +47,10 @@
 	void (*ack)(unsigned int irq);
 	void (*end)(unsigned int irq);
 	void (*set_affinity)(unsigned int irq, cpumask_t dest);
+	/* Currently used only by UML, might disappear one day.*/
+#ifdef CONFIG_IRQ_RELEASE_METHOD
+	void (*release)(unsigned int irq, void *dev_id);
+#endif
 };
 
 typedef struct hw_interrupt_type  hw_irq_controller;
diff --git a/include/linux/mm.h b/include/linux/mm.h
index 17518fe..1813b16 100644
--- a/include/linux/mm.h
+++ b/include/linux/mm.h
@@ -691,6 +691,12 @@
 extern void si_meminfo(struct sysinfo * val);
 extern void si_meminfo_node(struct sysinfo *val, int nid);
 
+#ifdef CONFIG_NUMA
+extern void setup_per_cpu_pageset(void);
+#else
+static inline void setup_per_cpu_pageset(void) {}
+#endif
+
 /* prio_tree.c */
 void vma_prio_tree_add(struct vm_area_struct *, struct vm_area_struct *old);
 void vma_prio_tree_insert(struct vm_area_struct *, struct prio_tree_root *);
diff --git a/include/linux/mmzone.h b/include/linux/mmzone.h
index e530c6c..4733d35 100644
--- a/include/linux/mmzone.h
+++ b/include/linux/mmzone.h
@@ -63,6 +63,12 @@
 #endif
 } ____cacheline_aligned_in_smp;
 
+#ifdef CONFIG_NUMA
+#define zone_pcp(__z, __cpu) ((__z)->pageset[(__cpu)])
+#else
+#define zone_pcp(__z, __cpu) (&(__z)->pageset[(__cpu)])
+#endif
+
 #define ZONE_DMA		0
 #define ZONE_NORMAL		1
 #define ZONE_HIGHMEM		2
@@ -122,8 +128,11 @@
 	 */
 	unsigned long		lowmem_reserve[MAX_NR_ZONES];
 
+#ifdef CONFIG_NUMA
+	struct per_cpu_pageset	*pageset[NR_CPUS];
+#else
 	struct per_cpu_pageset	pageset[NR_CPUS];
-
+#endif
 	/*
 	 * free areas of different sizes
 	 */
@@ -145,6 +154,14 @@
 	int			all_unreclaimable; /* All pages pinned */
 
 	/*
+	 * Does the allocator try to reclaim pages from the zone as soon
+	 * as it fails a watermark_ok() in __alloc_pages?
+	 */
+	int			reclaim_pages;
+	/* A count of how many reclaimers are scanning this zone */
+	atomic_t		reclaim_in_progress;
+
+	/*
 	 * prev_priority holds the scanning priority for this zone.  It is
 	 * defined as the scanning priority at which we achieved our reclaim
 	 * target at the previous try_to_free_pages() or balance_pgdat()
@@ -381,7 +398,7 @@
 
 #include <linux/topology.h>
 /* Returns the number of the current Node. */
-#define numa_node_id()		(cpu_to_node(_smp_processor_id()))
+#define numa_node_id()		(cpu_to_node(raw_smp_processor_id()))
 
 #ifndef CONFIG_DISCONTIGMEM
 
diff --git a/include/linux/netfilter_ipv4.h b/include/linux/netfilter_ipv4.h
index 9e57500..3ebc36a 100644
--- a/include/linux/netfilter_ipv4.h
+++ b/include/linux/netfilter_ipv4.h
@@ -75,12 +75,6 @@
 #define SO_ORIGINAL_DST 80
 
 #ifdef __KERNEL__
-#ifdef CONFIG_NETFILTER_DEBUG
-void nf_debug_ip_local_deliver(struct sk_buff *skb);
-void nf_debug_ip_loopback_xmit(struct sk_buff *newskb);
-void nf_debug_ip_finish_output2(struct sk_buff *skb);
-#endif /*CONFIG_NETFILTER_DEBUG*/
-
 extern int ip_route_me_harder(struct sk_buff **pskb);
 
 /* Call this before modifying an existing IP packet: ensures it is
diff --git a/include/linux/netfilter_ipv4/ip_conntrack_core.h b/include/linux/netfilter_ipv4/ip_conntrack_core.h
index d84be02..694aec9 100644
--- a/include/linux/netfilter_ipv4/ip_conntrack_core.h
+++ b/include/linux/netfilter_ipv4/ip_conntrack_core.h
@@ -1,7 +1,6 @@
 #ifndef _IP_CONNTRACK_CORE_H
 #define _IP_CONNTRACK_CORE_H
 #include <linux/netfilter.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 /* This header is used to share core functionality between the
    standalone connection tracking module, and the compatibility layer's use
@@ -47,6 +46,6 @@
 
 extern struct list_head *ip_conntrack_hash;
 extern struct list_head ip_conntrack_expect_list;
-DECLARE_RWLOCK_EXTERN(ip_conntrack_lock);
+extern rwlock_t ip_conntrack_lock;
 #endif /* _IP_CONNTRACK_CORE_H */
 
diff --git a/include/linux/netfilter_ipv4/ip_nat.h b/include/linux/netfilter_ipv4/ip_nat.h
index 2b72b86..e201ec6 100644
--- a/include/linux/netfilter_ipv4/ip_nat.h
+++ b/include/linux/netfilter_ipv4/ip_nat.h
@@ -50,10 +50,9 @@
 
 #ifdef __KERNEL__
 #include <linux/list.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 /* Protects NAT hash tables, and NAT-private part of conntracks. */
-DECLARE_RWLOCK_EXTERN(ip_nat_lock);
+extern rwlock_t ip_nat_lock;
 
 /* The structure embedded in the conntrack structure. */
 struct ip_nat_info
diff --git a/include/linux/netfilter_ipv4/listhelp.h b/include/linux/netfilter_ipv4/listhelp.h
index f2ae7c5..360429f 100644
--- a/include/linux/netfilter_ipv4/listhelp.h
+++ b/include/linux/netfilter_ipv4/listhelp.h
@@ -2,7 +2,6 @@
 #define _LISTHELP_H
 #include <linux/config.h>
 #include <linux/list.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 /* Header to do more comprehensive job than linux/list.h; assume list
    is first entry in structure. */
diff --git a/include/linux/netfilter_ipv4/lockhelp.h b/include/linux/netfilter_ipv4/lockhelp.h
deleted file mode 100644
index a328863..0000000
--- a/include/linux/netfilter_ipv4/lockhelp.h
+++ /dev/null
@@ -1,129 +0,0 @@
-#ifndef _LOCKHELP_H
-#define _LOCKHELP_H
-#include <linux/config.h>
-
-#include <linux/spinlock.h>
-#include <asm/atomic.h>
-#include <linux/interrupt.h>
-#include <linux/smp.h>
-
-/* Header to do help in lock debugging. */
-
-#ifdef CONFIG_NETFILTER_DEBUG
-struct spinlock_debug
-{
-	spinlock_t l;
-	atomic_t locked_by;
-};
-
-struct rwlock_debug
-{
-	rwlock_t l;
-	long read_locked_map;
-	long write_locked_map;
-};
-
-#define DECLARE_LOCK(l) 						\
-struct spinlock_debug l = { SPIN_LOCK_UNLOCKED, ATOMIC_INIT(-1) }
-#define DECLARE_LOCK_EXTERN(l) 			\
-extern struct spinlock_debug l
-#define DECLARE_RWLOCK(l)				\
-struct rwlock_debug l = { RW_LOCK_UNLOCKED, 0, 0 }
-#define DECLARE_RWLOCK_EXTERN(l)		\
-extern struct rwlock_debug l
-
-#define MUST_BE_LOCKED(l)						\
-do { if (atomic_read(&(l)->locked_by) != smp_processor_id())		\
-	printk("ASSERT %s:%u %s unlocked\n", __FILE__, __LINE__, #l);	\
-} while(0)
-
-#define MUST_BE_UNLOCKED(l)						\
-do { if (atomic_read(&(l)->locked_by) == smp_processor_id())		\
-	printk("ASSERT %s:%u %s locked\n", __FILE__, __LINE__, #l);	\
-} while(0)
-
-/* Write locked OK as well. */
-#define MUST_BE_READ_LOCKED(l)						    \
-do { if (!((l)->read_locked_map & (1UL << smp_processor_id()))		    \
-	 && !((l)->write_locked_map & (1UL << smp_processor_id())))	    \
-	printk("ASSERT %s:%u %s not readlocked\n", __FILE__, __LINE__, #l); \
-} while(0)
-
-#define MUST_BE_WRITE_LOCKED(l)						     \
-do { if (!((l)->write_locked_map & (1UL << smp_processor_id())))	     \
-	printk("ASSERT %s:%u %s not writelocked\n", __FILE__, __LINE__, #l); \
-} while(0)
-
-#define MUST_BE_READ_WRITE_UNLOCKED(l)					  \
-do { if ((l)->read_locked_map & (1UL << smp_processor_id()))		  \
-	printk("ASSERT %s:%u %s readlocked\n", __FILE__, __LINE__, #l);	  \
- else if ((l)->write_locked_map & (1UL << smp_processor_id()))		  \
-	 printk("ASSERT %s:%u %s writelocked\n", __FILE__, __LINE__, #l); \
-} while(0)
-
-#define LOCK_BH(lk)						\
-do {								\
-	MUST_BE_UNLOCKED(lk);					\
-	spin_lock_bh(&(lk)->l);					\
-	atomic_set(&(lk)->locked_by, smp_processor_id());	\
-} while(0)
-
-#define UNLOCK_BH(lk)				\
-do {						\
-	MUST_BE_LOCKED(lk);			\
-	atomic_set(&(lk)->locked_by, -1);	\
-	spin_unlock_bh(&(lk)->l);		\
-} while(0)
-
-#define READ_LOCK(lk) 						\
-do {								\
-	MUST_BE_READ_WRITE_UNLOCKED(lk);			\
-	read_lock_bh(&(lk)->l);					\
-	set_bit(smp_processor_id(), &(lk)->read_locked_map);	\
-} while(0)
-
-#define WRITE_LOCK(lk)							  \
-do {									  \
-	MUST_BE_READ_WRITE_UNLOCKED(lk);				  \
-	write_lock_bh(&(lk)->l);					  \
-	set_bit(smp_processor_id(), &(lk)->write_locked_map);		  \
-} while(0)
-
-#define READ_UNLOCK(lk)							\
-do {									\
-	if (!((lk)->read_locked_map & (1UL << smp_processor_id())))	\
-		printk("ASSERT: %s:%u %s not readlocked\n", 		\
-		       __FILE__, __LINE__, #lk);			\
-	clear_bit(smp_processor_id(), &(lk)->read_locked_map);		\
-	read_unlock_bh(&(lk)->l);					\
-} while(0)
-
-#define WRITE_UNLOCK(lk)					\
-do {								\
-	MUST_BE_WRITE_LOCKED(lk);				\
-	clear_bit(smp_processor_id(), &(lk)->write_locked_map);	\
-	write_unlock_bh(&(lk)->l);				\
-} while(0)
-
-#else
-#define DECLARE_LOCK(l) spinlock_t l = SPIN_LOCK_UNLOCKED
-#define DECLARE_LOCK_EXTERN(l) extern spinlock_t l
-#define DECLARE_RWLOCK(l) rwlock_t l = RW_LOCK_UNLOCKED
-#define DECLARE_RWLOCK_EXTERN(l) extern rwlock_t l
-
-#define MUST_BE_LOCKED(l)
-#define MUST_BE_UNLOCKED(l)
-#define MUST_BE_READ_LOCKED(l)
-#define MUST_BE_WRITE_LOCKED(l)
-#define MUST_BE_READ_WRITE_UNLOCKED(l)
-
-#define LOCK_BH(l) spin_lock_bh(l)
-#define UNLOCK_BH(l) spin_unlock_bh(l)
-
-#define READ_LOCK(l) read_lock_bh(l)
-#define WRITE_LOCK(l) write_lock_bh(l)
-#define READ_UNLOCK(l) read_unlock_bh(l)
-#define WRITE_UNLOCK(l) write_unlock_bh(l)
-#endif /*CONFIG_NETFILTER_DEBUG*/
-
-#endif /* _LOCKHELP_H */
diff --git a/include/linux/netlink.h b/include/linux/netlink.h
index 561d4dc..3029cad 100644
--- a/include/linux/netlink.h
+++ b/include/linux/netlink.h
@@ -147,7 +147,7 @@
 	int		(*dump)(struct sk_buff * skb, struct netlink_callback *cb);
 	int		(*done)(struct netlink_callback *cb);
 	int		family;
-	long		args[4];
+	long		args[5];
 };
 
 struct netlink_notify
diff --git a/include/linux/page-flags.h b/include/linux/page-flags.h
index 39ab8c6..f5a6695 100644
--- a/include/linux/page-flags.h
+++ b/include/linux/page-flags.h
@@ -61,21 +61,20 @@
 #define PG_active		 6
 #define PG_slab			 7	/* slab debug (Suparna wants this) */
 
-#define PG_highmem		 8
-#define PG_checked		 9	/* kill me in 2.5.<early>. */
-#define PG_arch_1		10
-#define PG_reserved		11
+#define PG_checked		 8	/* kill me in 2.5.<early>. */
+#define PG_arch_1		 9
+#define PG_reserved		10
+#define PG_private		11	/* Has something at ->private */
 
-#define PG_private		12	/* Has something at ->private */
-#define PG_writeback		13	/* Page is under writeback */
-#define PG_nosave		14	/* Used for system suspend/resume */
-#define PG_compound		15	/* Part of a compound page */
+#define PG_writeback		12	/* Page is under writeback */
+#define PG_nosave		13	/* Used for system suspend/resume */
+#define PG_compound		14	/* Part of a compound page */
+#define PG_swapcache		15	/* Swap page: swp_entry_t in private */
 
-#define PG_swapcache		16	/* Swap page: swp_entry_t in private */
-#define PG_mappedtodisk		17	/* Has blocks allocated on-disk */
-#define PG_reclaim		18	/* To be reclaimed asap */
-#define PG_nosave_free		19	/* Free, should not be written */
-#define PG_uncached		20	/* Page has been mapped as uncached */
+#define PG_mappedtodisk		16	/* Has blocks allocated on-disk */
+#define PG_reclaim		17	/* To be reclaimed asap */
+#define PG_nosave_free		18	/* Free, should not be written */
+#define PG_uncached		19	/* Page has been mapped as uncached */
 
 /*
  * Global page accounting.  One instance per CPU.  Only unsigned longs are
@@ -136,8 +135,8 @@
 
 extern void get_page_state(struct page_state *ret);
 extern void get_full_page_state(struct page_state *ret);
-extern unsigned long __read_page_state(unsigned offset);
-extern void __mod_page_state(unsigned offset, unsigned long delta);
+extern unsigned long __read_page_state(unsigned long offset);
+extern void __mod_page_state(unsigned long offset, unsigned long delta);
 
 #define read_page_state(member) \
 	__read_page_state(offsetof(struct page_state, member))
@@ -215,7 +214,7 @@
 #define TestSetPageSlab(page)	test_and_set_bit(PG_slab, &(page)->flags)
 
 #ifdef CONFIG_HIGHMEM
-#define PageHighMem(page)	test_bit(PG_highmem, &(page)->flags)
+#define PageHighMem(page)	is_highmem(page_zone(page))
 #else
 #define PageHighMem(page)	0 /* needed to optimize away at compile time */
 #endif
diff --git a/include/linux/pagemap.h b/include/linux/pagemap.h
index 0422031..d9a2564 100644
--- a/include/linux/pagemap.h
+++ b/include/linux/pagemap.h
@@ -52,12 +52,12 @@
 
 static inline struct page *page_cache_alloc(struct address_space *x)
 {
-	return alloc_pages(mapping_gfp_mask(x), 0);
+	return alloc_pages(mapping_gfp_mask(x)|__GFP_NORECLAIM, 0);
 }
 
 static inline struct page *page_cache_alloc_cold(struct address_space *x)
 {
-	return alloc_pages(mapping_gfp_mask(x)|__GFP_COLD, 0);
+	return alloc_pages(mapping_gfp_mask(x)|__GFP_COLD|__GFP_NORECLAIM, 0);
 }
 
 typedef int filler_t(void *, struct page *);
diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h
index b8b4ebf..63e89e4 100644
--- a/include/linux/pci_ids.h
+++ b/include/linux/pci_ids.h
@@ -575,6 +575,7 @@
 #define PCI_DEVICE_ID_CT_65550		0x00e0
 #define PCI_DEVICE_ID_CT_65554		0x00e4
 #define PCI_DEVICE_ID_CT_65555		0x00e5
+#define PCI_DEVICE_ID_CT_69000		0x00c0
 
 #define PCI_VENDOR_ID_MIRO		0x1031
 #define PCI_DEVICE_ID_MIRO_36050	0x5601
diff --git a/include/linux/raid/bitmap.h b/include/linux/raid/bitmap.h
new file mode 100644
index 0000000..e24b74b
--- /dev/null
+++ b/include/linux/raid/bitmap.h
@@ -0,0 +1,273 @@
+/*
+ * bitmap.h: Copyright (C) Peter T. Breuer (ptb@ot.uc3m.es) 2003
+ *
+ * additions: Copyright (C) 2003-2004, Paul Clements, SteelEye Technology, Inc.
+ */
+#ifndef BITMAP_H
+#define BITMAP_H 1
+
+#define BITMAP_MAJOR 3
+#define BITMAP_MINOR 38
+
+/*
+ * in-memory bitmap:
+ *
+ * Use 16 bit block counters to track pending writes to each "chunk".
+ * The 2 high order bits are special-purpose, the first is a flag indicating
+ * whether a resync is needed.  The second is a flag indicating whether a
+ * resync is active.
+ * This means that the counter is actually 14 bits:
+ *
+ * +--------+--------+------------------------------------------------+
+ * | resync | resync |               counter                          |
+ * | needed | active |                                                |
+ * |  (0-1) |  (0-1) |              (0-16383)                         |
+ * +--------+--------+------------------------------------------------+
+ *
+ * The "resync needed" bit is set when:
+ *    a '1' bit is read from storage at startup.
+ *    a write request fails on some drives
+ *    a resync is aborted on a chunk with 'resync active' set
+ * It is cleared (and resync-active set) when a resync starts across all drives
+ * of the chunk.
+ *
+ *
+ * The "resync active" bit is set when:
+ *    a resync is started on all drives, and resync_needed is set.
+ *       resync_needed will be cleared (as long as resync_active wasn't already set).
+ * It is cleared when a resync completes.
+ *
+ * The counter counts pending write requests, plus the on-disk bit.
+ * When the counter is '1' and the resync bits are clear, the on-disk
+ * bit can be cleared aswell, thus setting the counter to 0.
+ * When we set a bit, or in the counter (to start a write), if the fields is
+ * 0, we first set the disk bit and set the counter to 1.
+ *
+ * If the counter is 0, the on-disk bit is clear and the stipe is clean
+ * Anything that dirties the stipe pushes the counter to 2 (at least)
+ * and sets the on-disk bit (lazily).
+ * If a periodic sweep find the counter at 2, it is decremented to 1.
+ * If the sweep find the counter at 1, the on-disk bit is cleared and the
+ * counter goes to zero.
+ *
+ * Also, we'll hijack the "map" pointer itself and use it as two 16 bit block
+ * counters as a fallback when "page" memory cannot be allocated:
+ *
+ * Normal case (page memory allocated):
+ *
+ *     page pointer (32-bit)
+ *
+ *     [ ] ------+
+ *               |
+ *               +-------> [   ][   ]..[   ] (4096 byte page == 2048 counters)
+ *                          c1   c2    c2048
+ *
+ * Hijacked case (page memory allocation failed):
+ *
+ *     hijacked page pointer (32-bit)
+ *
+ *     [		  ][		  ] (no page memory allocated)
+ *      counter #1 (16-bit) counter #2 (16-bit)
+ *
+ */
+
+#ifdef __KERNEL__
+
+#define PAGE_BITS (PAGE_SIZE << 3)
+#define PAGE_BIT_SHIFT (PAGE_SHIFT + 3)
+
+typedef __u16 bitmap_counter_t;
+#define COUNTER_BITS 16
+#define COUNTER_BIT_SHIFT 4
+#define COUNTER_BYTE_RATIO (COUNTER_BITS / 8)
+#define COUNTER_BYTE_SHIFT (COUNTER_BIT_SHIFT - 3)
+
+#define NEEDED_MASK ((bitmap_counter_t) (1 << (COUNTER_BITS - 1)))
+#define RESYNC_MASK ((bitmap_counter_t) (1 << (COUNTER_BITS - 2)))
+#define COUNTER_MAX ((bitmap_counter_t) RESYNC_MASK - 1)
+#define NEEDED(x) (((bitmap_counter_t) x) & NEEDED_MASK)
+#define RESYNC(x) (((bitmap_counter_t) x) & RESYNC_MASK)
+#define COUNTER(x) (((bitmap_counter_t) x) & COUNTER_MAX)
+
+/* how many counters per page? */
+#define PAGE_COUNTER_RATIO (PAGE_BITS / COUNTER_BITS)
+/* same, except a shift value for more efficient bitops */
+#define PAGE_COUNTER_SHIFT (PAGE_BIT_SHIFT - COUNTER_BIT_SHIFT)
+/* same, except a mask value for more efficient bitops */
+#define PAGE_COUNTER_MASK  (PAGE_COUNTER_RATIO - 1)
+
+#define BITMAP_BLOCK_SIZE 512
+#define BITMAP_BLOCK_SHIFT 9
+
+/* how many blocks per chunk? (this is variable) */
+#define CHUNK_BLOCK_RATIO(bitmap) ((bitmap)->chunksize >> BITMAP_BLOCK_SHIFT)
+#define CHUNK_BLOCK_SHIFT(bitmap) ((bitmap)->chunkshift - BITMAP_BLOCK_SHIFT)
+#define CHUNK_BLOCK_MASK(bitmap) (CHUNK_BLOCK_RATIO(bitmap) - 1)
+
+/* when hijacked, the counters and bits represent even larger "chunks" */
+/* there will be 1024 chunks represented by each counter in the page pointers */
+#define PAGEPTR_BLOCK_RATIO(bitmap) \
+			(CHUNK_BLOCK_RATIO(bitmap) << PAGE_COUNTER_SHIFT >> 1)
+#define PAGEPTR_BLOCK_SHIFT(bitmap) \
+			(CHUNK_BLOCK_SHIFT(bitmap) + PAGE_COUNTER_SHIFT - 1)
+#define PAGEPTR_BLOCK_MASK(bitmap) (PAGEPTR_BLOCK_RATIO(bitmap) - 1)
+
+/*
+ * on-disk bitmap:
+ *
+ * Use one bit per "chunk" (block set). We do the disk I/O on the bitmap
+ * file a page at a time. There's a superblock at the start of the file.
+ */
+
+/* map chunks (bits) to file pages - offset by the size of the superblock */
+#define CHUNK_BIT_OFFSET(chunk) ((chunk) + (sizeof(bitmap_super_t) << 3))
+
+#endif
+
+/*
+ * bitmap structures:
+ */
+
+#define BITMAP_MAGIC 0x6d746962
+
+/* use these for bitmap->flags and bitmap->sb->state bit-fields */
+enum bitmap_state {
+	BITMAP_ACTIVE = 0x001, /* the bitmap is in use */
+	BITMAP_STALE  = 0x002  /* the bitmap file is out of date or had -EIO */
+};
+
+/* the superblock at the front of the bitmap file -- little endian */
+typedef struct bitmap_super_s {
+	__u32 magic;        /*  0  BITMAP_MAGIC */
+	__u32 version;      /*  4  the bitmap major for now, could change... */
+	__u8  uuid[16];     /*  8  128 bit uuid - must match md device uuid */
+	__u64 events;       /* 24  event counter for the bitmap (1)*/
+	__u64 events_cleared;/*32  event counter when last bit cleared (2) */
+	__u64 sync_size;    /* 40  the size of the md device's sync range(3) */
+	__u32 state;        /* 48  bitmap state information */
+	__u32 chunksize;    /* 52  the bitmap chunk size in bytes */
+	__u32 daemon_sleep; /* 56  seconds between disk flushes */
+
+	__u8  pad[256 - 60]; /* set to zero */
+} bitmap_super_t;
+
+/* notes:
+ * (1) This event counter is updated before the eventcounter in the md superblock
+ *    When a bitmap is loaded, it is only accepted if this event counter is equal
+ *    to, or one greater than, the event counter in the superblock.
+ * (2) This event counter is updated when the other one is *if*and*only*if* the
+ *    array is not degraded.  As bits are not cleared when the array is degraded,
+ *    this represents the last time that any bits were cleared.
+ *    If a device is being added that has an event count with this value or
+ *    higher, it is accepted as conforming to the bitmap.
+ * (3)This is the number of sectors represented by the bitmap, and is the range that
+ *    resync happens across.  For raid1 and raid5/6 it is the size of individual
+ *    devices.  For raid10 it is the size of the array.
+ */
+
+#ifdef __KERNEL__
+
+/* the in-memory bitmap is represented by bitmap_pages */
+struct bitmap_page {
+	/*
+	 * map points to the actual memory page
+	 */
+	char *map;
+	/*
+	 * in emergencies (when map cannot be alloced), hijack the map
+	 * pointer and use it as two counters itself
+	 */
+	unsigned int hijacked:1;
+	/*
+	 * count of dirty bits on the page
+	 */
+	unsigned int  count:31;
+};
+
+/* keep track of bitmap file pages that have pending writes on them */
+struct page_list {
+	struct list_head list;
+	struct page *page;
+};
+
+/* the main bitmap structure - one per mddev */
+struct bitmap {
+	struct bitmap_page *bp;
+	unsigned long pages; /* total number of pages in the bitmap */
+	unsigned long missing_pages; /* number of pages not yet allocated */
+
+	mddev_t *mddev; /* the md device that the bitmap is for */
+
+	int counter_bits; /* how many bits per block counter */
+
+	/* bitmap chunksize -- how much data does each bit represent? */
+	unsigned long chunksize;
+	unsigned long chunkshift; /* chunksize = 2^chunkshift (for bitops) */
+	unsigned long chunks; /* total number of data chunks for the array */
+
+	/* We hold a count on the chunk currently being synced, and drop
+	 * it when the last block is started.  If the resync is aborted
+	 * midway, we need to be able to drop that count, so we remember
+	 * the counted chunk..
+	 */
+	unsigned long syncchunk;
+
+	__u64	events_cleared;
+
+	/* bitmap spinlock */
+	spinlock_t lock;
+
+	long offset; /* offset from superblock if file is NULL */
+	struct file *file; /* backing disk file */
+	struct page *sb_page; /* cached copy of the bitmap file superblock */
+	struct page **filemap; /* list of cache pages for the file */
+	unsigned long *filemap_attr; /* attributes associated w/ filemap pages */
+	unsigned long file_pages; /* number of pages in the file */
+
+	unsigned long flags;
+
+	/*
+	 * the bitmap daemon - periodically wakes up and sweeps the bitmap
+	 * file, cleaning up bits and flushing out pages to disk as necessary
+	 */
+	unsigned long daemon_lastrun; /* jiffies of last run */
+	unsigned long daemon_sleep; /* how many seconds between updates? */
+
+	/*
+	 * bitmap_writeback_daemon waits for file-pages that have been written,
+	 * as there is no way to get a call-back when a page write completes.
+	 */
+	mdk_thread_t *writeback_daemon;
+	spinlock_t write_lock;
+	wait_queue_head_t write_wait;
+	struct list_head complete_pages;
+	mempool_t *write_pool;
+};
+
+/* the bitmap API */
+
+/* these are used only by md/bitmap */
+int  bitmap_create(mddev_t *mddev);
+void bitmap_destroy(mddev_t *mddev);
+int  bitmap_active(struct bitmap *bitmap);
+
+char *file_path(struct file *file, char *buf, int count);
+void bitmap_print_sb(struct bitmap *bitmap);
+int bitmap_update_sb(struct bitmap *bitmap);
+
+int  bitmap_setallbits(struct bitmap *bitmap);
+void bitmap_write_all(struct bitmap *bitmap);
+
+/* these are exported */
+int bitmap_startwrite(struct bitmap *bitmap, sector_t offset, unsigned long sectors);
+void bitmap_endwrite(struct bitmap *bitmap, sector_t offset, unsigned long sectors,
+		     int success);
+int bitmap_start_sync(struct bitmap *bitmap, sector_t offset, int *blocks);
+void bitmap_end_sync(struct bitmap *bitmap, sector_t offset, int *blocks, int aborted);
+void bitmap_close_sync(struct bitmap *bitmap);
+
+int bitmap_unplug(struct bitmap *bitmap);
+int bitmap_daemon_work(struct bitmap *bitmap);
+#endif
+
+#endif
diff --git a/include/linux/raid/md.h b/include/linux/raid/md.h
index a6a67d1..ffa316c 100644
--- a/include/linux/raid/md.h
+++ b/include/linux/raid/md.h
@@ -60,7 +60,14 @@
  */
 #define MD_MAJOR_VERSION                0
 #define MD_MINOR_VERSION                90
-#define MD_PATCHLEVEL_VERSION           1
+/*
+ * MD_PATCHLEVEL_VERSION indicates kernel functionality.
+ * >=1 means different superblock formats are selectable using SET_ARRAY_INFO
+ *     and major_version/minor_version accordingly
+ * >=2 means that Internal bitmaps are supported by setting MD_SB_BITMAP_PRESENT
+ *     in the super status byte
+ */
+#define MD_PATCHLEVEL_VERSION           2
 
 extern int register_md_personality (int p_num, mdk_personality_t *p);
 extern int unregister_md_personality (int p_num);
@@ -69,7 +76,7 @@
 extern void md_unregister_thread (mdk_thread_t *thread);
 extern void md_wakeup_thread(mdk_thread_t *thread);
 extern void md_check_recovery(mddev_t *mddev);
-extern void md_write_start(mddev_t *mddev);
+extern void md_write_start(mddev_t *mddev, struct bio *bi);
 extern void md_write_end(mddev_t *mddev);
 extern void md_handle_safemode(mddev_t *mddev);
 extern void md_done_sync(mddev_t *mddev, int blocks, int ok);
@@ -78,6 +85,12 @@
 
 extern void md_print_devices (void);
 
+extern void md_super_write(mddev_t *mddev, mdk_rdev_t *rdev,
+			   sector_t sector, int size, struct page *page);
+extern int sync_page_io(struct block_device *bdev, sector_t sector, int size,
+			struct page *page, int rw);
+
+
 #define MD_BUG(x...) { printk("md: bug in file %s, line %d\n", __FILE__, __LINE__); md_print_devices(); }
 
 #endif 
diff --git a/include/linux/raid/md_k.h b/include/linux/raid/md_k.h
index c9a0d40..8c14ba5 100644
--- a/include/linux/raid/md_k.h
+++ b/include/linux/raid/md_k.h
@@ -15,6 +15,9 @@
 #ifndef _MD_K_H
 #define _MD_K_H
 
+/* and dm-bio-list.h is not under include/linux because.... ??? */
+#include "../../../drivers/md/dm-bio-list.h"
+
 #define MD_RESERVED       0UL
 #define LINEAR            1UL
 #define RAID0             2UL
@@ -180,6 +183,10 @@
 
 	int desc_nr;			/* descriptor index in the superblock */
 	int raid_disk;			/* role of device in array */
+	int saved_raid_disk;		/* role that device used to have in the
+					 * array and could again if we did a partial
+					 * resync from the bitmap
+					 */
 
 	atomic_t	nr_pending;	/* number of pending requests.
 					 * only maintained for arrays that
@@ -252,6 +259,11 @@
 	atomic_t			recovery_active; /* blocks scheduled, but not written */
 	wait_queue_head_t		recovery_wait;
 	sector_t			recovery_cp;
+
+	spinlock_t			write_lock;
+	wait_queue_head_t		sb_wait;	/* for waiting on superblock updates */
+	atomic_t			pending_writes;	/* number of active superblock writes */
+
 	unsigned int			safemode;	/* if set, update "clean" superblock
 							 * when no writes pending.
 							 */ 
@@ -260,6 +272,13 @@
 	atomic_t			writes_pending; 
 	request_queue_t			*queue;	/* for plugging ... */
 
+	struct bitmap                   *bitmap; /* the bitmap for the device */
+	struct file			*bitmap_file; /* the bitmap file */
+	long				bitmap_offset; /* offset from superblock of
+							* start of bitmap. May be
+							* negative, but not '0'
+							*/
+
 	struct list_head		all_mddevs;
 };
 
@@ -291,7 +310,7 @@
 	int (*hot_add_disk) (mddev_t *mddev, mdk_rdev_t *rdev);
 	int (*hot_remove_disk) (mddev_t *mddev, int number);
 	int (*spare_active) (mddev_t *mddev);
-	int (*sync_request)(mddev_t *mddev, sector_t sector_nr, int go_faster);
+	sector_t (*sync_request)(mddev_t *mddev, sector_t sector_nr, int *skipped, int go_faster);
 	int (*resize) (mddev_t *mddev, sector_t sectors);
 	int (*reshape) (mddev_t *mddev, int raid_disks);
 	int (*reconfig) (mddev_t *mddev, int layout, int chunk_size);
@@ -334,6 +353,7 @@
 	unsigned long           flags;
 	struct completion	*event;
 	struct task_struct	*tsk;
+	unsigned long		timeout;
 	const char		*name;
 } mdk_thread_t;
 
diff --git a/include/linux/raid/md_p.h b/include/linux/raid/md_p.h
index 8ba95d6..dc65cd4 100644
--- a/include/linux/raid/md_p.h
+++ b/include/linux/raid/md_p.h
@@ -96,6 +96,7 @@
 #define MD_SB_CLEAN		0
 #define MD_SB_ERRORS		1
 
+#define	MD_SB_BITMAP_PRESENT	8 /* bitmap may be present nearby */
 typedef struct mdp_superblock_s {
 	/*
 	 * Constant generic information
@@ -184,7 +185,7 @@
 	/* constant array information - 128 bytes */
 	__u32	magic;		/* MD_SB_MAGIC: 0xa92b4efc - little endian */
 	__u32	major_version;	/* 1 */
-	__u32	feature_map;	/* 0 for now */
+	__u32	feature_map;	/* bit 0 set if 'bitmap_offset' is meaningful */
 	__u32	pad0;		/* always set to 0 when writing */
 
 	__u8	set_uuid[16];	/* user-space generated. */
@@ -197,7 +198,11 @@
 
 	__u32	chunksize;	/* in 512byte sectors */
 	__u32	raid_disks;
-	__u8	pad1[128-96];	/* set to 0 when written */
+	__u32	bitmap_offset;	/* sectors after start of superblock that bitmap starts
+				 * NOTE: signed, so bitmap can be before superblock
+				 * only meaningful of feature_map[0] is set.
+				 */
+	__u8	pad1[128-100];	/* set to 0 when written */
 
 	/* constant this-device information - 64 bytes */
 	__u64	data_offset;	/* sector start of data, often 0 */
diff --git a/include/linux/raid/md_u.h b/include/linux/raid/md_u.h
index a2df5c2..81da20c 100644
--- a/include/linux/raid/md_u.h
+++ b/include/linux/raid/md_u.h
@@ -23,6 +23,7 @@
 #define GET_DISK_INFO		_IOR (MD_MAJOR, 0x12, mdu_disk_info_t)
 #define PRINT_RAID_DEBUG	_IO (MD_MAJOR, 0x13)
 #define RAID_AUTORUN		_IO (MD_MAJOR, 0x14)
+#define GET_BITMAP_FILE		_IOR (MD_MAJOR, 0x15, mdu_bitmap_file_t)
 
 /* configuration */
 #define CLEAR_ARRAY		_IO (MD_MAJOR, 0x20)
@@ -36,6 +37,7 @@
 #define HOT_ADD_DISK		_IO (MD_MAJOR, 0x28)
 #define SET_DISK_FAULTY		_IO (MD_MAJOR, 0x29)
 #define HOT_GENERATE_ERROR	_IO (MD_MAJOR, 0x2a)
+#define SET_BITMAP_FILE		_IOW (MD_MAJOR, 0x2b, int)
 
 /* usage */
 #define RUN_ARRAY		_IOW (MD_MAJOR, 0x30, mdu_param_t)
@@ -106,6 +108,11 @@
 
 } mdu_start_info_t;
 
+typedef struct mdu_bitmap_file_s
+{
+	char pathname[4096];
+} mdu_bitmap_file_t;
+
 typedef struct mdu_param_s
 {
 	int			personality;	/* 1,2,3,4 */
diff --git a/include/linux/raid/raid1.h b/include/linux/raid/raid1.h
index abbfdd9..9d93cf1 100644
--- a/include/linux/raid/raid1.h
+++ b/include/linux/raid/raid1.h
@@ -36,12 +36,21 @@
 	spinlock_t		device_lock;
 
 	struct list_head	retry_list;
+	/* queue pending writes and submit them on unplug */
+	struct bio_list		pending_bio_list;
+	/* queue of writes that have been unplugged */
+	struct bio_list		flushing_bio_list;
+
 	/* for use when syncing mirrors: */
 
 	spinlock_t		resync_lock;
-	int nr_pending;
-	int barrier;
+	int			nr_pending;
+	int			barrier;
 	sector_t		next_resync;
+	int			fullsync;  /* set to 1 if a full sync is needed,
+					    * (fresh device added).
+					    * Cleared when a sync completes.
+					    */
 
 	wait_queue_head_t	wait_idle;
 	wait_queue_head_t	wait_resume;
@@ -85,14 +94,17 @@
 	int			read_disk;
 
 	struct list_head	retry_list;
+	struct bitmap_update	*bitmap_update;
 	/*
 	 * if the IO is in WRITE direction, then multiple bios are used.
 	 * We choose the number when they are allocated.
 	 */
 	struct bio		*bios[0];
+	/* DO NOT PUT ANY NEW FIELDS HERE - bios array is contiguously alloced*/
 };
 
 /* bits for r1bio.state */
 #define	R1BIO_Uptodate	0
 #define	R1BIO_IsSync	1
+#define	R1BIO_Degraded	2
 #endif
diff --git a/include/linux/sched.h b/include/linux/sched.h
index 4dbb109..b58afd9 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -201,8 +201,8 @@
 arch_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
 			  unsigned long len, unsigned long pgoff,
 			  unsigned long flags);
-extern void arch_unmap_area(struct vm_area_struct *area);
-extern void arch_unmap_area_topdown(struct vm_area_struct *area);
+extern void arch_unmap_area(struct mm_struct *, unsigned long);
+extern void arch_unmap_area_topdown(struct mm_struct *, unsigned long);
 
 #define set_mm_counter(mm, member, value) (mm)->_##member = (value)
 #define get_mm_counter(mm, member) ((mm)->_##member)
@@ -218,9 +218,10 @@
 	unsigned long (*get_unmapped_area) (struct file *filp,
 				unsigned long addr, unsigned long len,
 				unsigned long pgoff, unsigned long flags);
-	void (*unmap_area) (struct vm_area_struct *area);
-	unsigned long mmap_base;		/* base of mmap area */
-	unsigned long free_area_cache;		/* first hole */
+	void (*unmap_area) (struct mm_struct *mm, unsigned long addr);
+        unsigned long mmap_base;		/* base of mmap area */
+        unsigned long cached_hole_size;         /* if non-zero, the largest hole below free_area_cache */
+	unsigned long free_area_cache;		/* first hole of size cached_hole_size or larger */
 	pgd_t * pgd;
 	atomic_t mm_users;			/* How many users with user space? */
 	atomic_t mm_count;			/* How many references to "struct mm_struct" (users count as 1) */
diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h
index cc04f5c..d7c839a 100644
--- a/include/linux/skbuff.h
+++ b/include/linux/skbuff.h
@@ -193,7 +193,6 @@
  *	@nfcache: Cache info
  *	@nfct: Associated connection, if any
  *	@nfctinfo: Relationship of this skb to the connection
- *	@nf_debug: Netfilter debugging
  *	@nf_bridge: Saved data about a bridged frame - see br_netfilter.c
  *      @private: Data which is private to the HIPPI implementation
  *	@tc_index: Traffic control index
@@ -264,9 +263,6 @@
 	__u32			nfcache;
 	__u32			nfctinfo;
 	struct nf_conntrack	*nfct;
-#ifdef CONFIG_NETFILTER_DEBUG
-        unsigned int		nf_debug;
-#endif
 #ifdef CONFIG_BRIDGE_NETFILTER
 	struct nf_bridge_info	*nf_bridge;
 #endif
@@ -1219,15 +1215,6 @@
 {
 	nf_conntrack_put(skb->nfct);
 	skb->nfct = NULL;
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug = 0;
-#endif
-}
-static inline void nf_reset_debug(struct sk_buff *skb)
-{
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug = 0;
-#endif
 }
 
 #ifdef CONFIG_BRIDGE_NETFILTER
diff --git a/include/linux/smp.h b/include/linux/smp.h
index dcf1db3..9dfa3ee 100644
--- a/include/linux/smp.h
+++ b/include/linux/smp.h
@@ -92,10 +92,7 @@
 /*
  *	These macros fold the SMP functionality into a single CPU system
  */
-
-#if !defined(__smp_processor_id) || !defined(CONFIG_PREEMPT)
-# define smp_processor_id()			0
-#endif
+#define raw_smp_processor_id()			0
 #define hard_smp_processor_id()			0
 #define smp_call_function(func,info,retry,wait)	({ 0; })
 #define on_each_cpu(func,info,retry,wait)	({ func(info); 0; })
@@ -106,30 +103,25 @@
 #endif /* !SMP */
 
 /*
- * DEBUG_PREEMPT support: check whether smp_processor_id() is being
- * used in a preemption-safe way.
+ * smp_processor_id(): get the current CPU ID.
  *
- * An architecture has to enable this debugging code explicitly.
- * It can do so by renaming the smp_processor_id() macro to
- * __smp_processor_id().  This should only be done after some minimal
- * testing, because usually there are a number of false positives
- * that an architecture will trigger.
+ * if DEBUG_PREEMPT is enabled the we check whether it is
+ * used in a preemption-safe way. (smp_processor_id() is safe
+ * if it's used in a preemption-off critical section, or in
+ * a thread that is bound to the current CPU.)
  *
- * To fix a false positive (i.e. smp_processor_id() use that the
- * debugging code reports but which use for some reason is legal),
- * change the smp_processor_id() reference to _smp_processor_id(),
- * which is the nondebug variant.  NOTE: don't use this to hack around
- * real bugs.
+ * NOTE: raw_smp_processor_id() is for internal use only
+ * (smp_processor_id() is the preferred variant), but in rare
+ * instances it might also be used to turn off false positives
+ * (i.e. smp_processor_id() use that the debugging code reports but
+ * which use for some reason is legal). Don't use this to hack around
+ * the warning message, as your code might not work under PREEMPT.
  */
-#ifdef __smp_processor_id
-# if defined(CONFIG_PREEMPT) && defined(CONFIG_DEBUG_PREEMPT)
-   extern unsigned int smp_processor_id(void);
-# else
-#  define smp_processor_id() __smp_processor_id()
-# endif
-# define _smp_processor_id() __smp_processor_id()
+#ifdef CONFIG_DEBUG_PREEMPT
+  extern unsigned int debug_smp_processor_id(void);
+# define smp_processor_id() debug_smp_processor_id()
 #else
-# define _smp_processor_id() smp_processor_id()
+# define smp_processor_id() raw_smp_processor_id()
 #endif
 
 #define get_cpu()		({ preempt_disable(); smp_processor_id(); })
diff --git a/include/linux/swap.h b/include/linux/swap.h
index 3bbc41b..2343f99 100644
--- a/include/linux/swap.h
+++ b/include/linux/swap.h
@@ -172,7 +172,8 @@
 extern void swap_setup(void);
 
 /* linux/mm/vmscan.c */
-extern int try_to_free_pages(struct zone **, unsigned int, unsigned int);
+extern int try_to_free_pages(struct zone **, unsigned int);
+extern int zone_reclaim(struct zone *, unsigned int, unsigned int);
 extern int shrink_all_memory(int);
 extern int vm_swappiness;
 
diff --git a/include/net/ip6_fib.h b/include/net/ip6_fib.h
index 3199045..a66e9de 100644
--- a/include/net/ip6_fib.h
+++ b/include/net/ip6_fib.h
@@ -167,14 +167,17 @@
 extern int			fib6_add(struct fib6_node *root,
 					 struct rt6_info *rt,
 					 struct nlmsghdr *nlh,
-					 void *rtattr);
+					 void *rtattr,
+					 struct netlink_skb_parms *req);
 
 extern int			fib6_del(struct rt6_info *rt,
 					 struct nlmsghdr *nlh,
-					 void *rtattr);
+					 void *rtattr,
+					 struct netlink_skb_parms *req);
 
 extern void			inet6_rt_notify(int event, struct rt6_info *rt,
-						struct nlmsghdr *nlh);
+						struct nlmsghdr *nlh,
+						struct netlink_skb_parms *req);
 
 extern void			fib6_run_gc(unsigned long dummy);
 
diff --git a/include/net/ip6_route.h b/include/net/ip6_route.h
index d5d1dd1..f920706 100644
--- a/include/net/ip6_route.h
+++ b/include/net/ip6_route.h
@@ -41,13 +41,16 @@
 
 extern int			ip6_route_add(struct in6_rtmsg *rtmsg,
 					      struct nlmsghdr *,
-					      void *rtattr);
+					      void *rtattr,
+					      struct netlink_skb_parms *req);
 extern int			ip6_ins_rt(struct rt6_info *,
 					   struct nlmsghdr *,
-					   void *rtattr);
+					   void *rtattr,
+					   struct netlink_skb_parms *req);
 extern int			ip6_del_rt(struct rt6_info *,
 					   struct nlmsghdr *,
-					   void *rtattr);
+					   void *rtattr,
+					   struct netlink_skb_parms *req);
 
 extern int			ip6_rt_addr_add(struct in6_addr *addr,
 						struct net_device *dev,
diff --git a/include/net/route.h b/include/net/route.h
index d34ca8f..c3cd069 100644
--- a/include/net/route.h
+++ b/include/net/route.h
@@ -107,7 +107,7 @@
 
 extern struct rt_cache_stat *rt_cache_stat;
 #define RT_CACHE_STAT_INC(field)					  \
-		(per_cpu_ptr(rt_cache_stat, _smp_processor_id())->field++)
+		(per_cpu_ptr(rt_cache_stat, raw_smp_processor_id())->field++)
 
 extern struct ip_rt_acct *ip_rt_acct;
 
diff --git a/include/net/snmp.h b/include/net/snmp.h
index a15ab25..a36bed8 100644
--- a/include/net/snmp.h
+++ b/include/net/snmp.h
@@ -128,18 +128,18 @@
 #define SNMP_STAT_USRPTR(name)	(name[1])
 
 #define SNMP_INC_STATS_BH(mib, field) 	\
-	(per_cpu_ptr(mib[0], _smp_processor_id())->mibs[field]++)
+	(per_cpu_ptr(mib[0], raw_smp_processor_id())->mibs[field]++)
 #define SNMP_INC_STATS_OFFSET_BH(mib, field, offset)	\
-	(per_cpu_ptr(mib[0], _smp_processor_id())->mibs[field + (offset)]++)
+	(per_cpu_ptr(mib[0], raw_smp_processor_id())->mibs[field + (offset)]++)
 #define SNMP_INC_STATS_USER(mib, field) \
-	(per_cpu_ptr(mib[1], _smp_processor_id())->mibs[field]++)
+	(per_cpu_ptr(mib[1], raw_smp_processor_id())->mibs[field]++)
 #define SNMP_INC_STATS(mib, field) 	\
-	(per_cpu_ptr(mib[!in_softirq()], _smp_processor_id())->mibs[field]++)
+	(per_cpu_ptr(mib[!in_softirq()], raw_smp_processor_id())->mibs[field]++)
 #define SNMP_DEC_STATS(mib, field) 	\
-	(per_cpu_ptr(mib[!in_softirq()], _smp_processor_id())->mibs[field]--)
+	(per_cpu_ptr(mib[!in_softirq()], raw_smp_processor_id())->mibs[field]--)
 #define SNMP_ADD_STATS_BH(mib, field, addend) 	\
-	(per_cpu_ptr(mib[0], _smp_processor_id())->mibs[field] += addend)
+	(per_cpu_ptr(mib[0], raw_smp_processor_id())->mibs[field] += addend)
 #define SNMP_ADD_STATS_USER(mib, field, addend) 	\
-	(per_cpu_ptr(mib[1], _smp_processor_id())->mibs[field] += addend)
+	(per_cpu_ptr(mib[1], raw_smp_processor_id())->mibs[field] += addend)
 
 #endif
diff --git a/init/main.c b/init/main.c
index 40bf367..d324801 100644
--- a/init/main.c
+++ b/init/main.c
@@ -490,6 +490,7 @@
 	vfs_caches_init_early();
 	mem_init();
 	kmem_cache_init();
+	setup_per_cpu_pageset();
 	numa_policy_init();
 	if (late_time_init)
 		late_time_init();
diff --git a/kernel/fork.c b/kernel/fork.c
index f42a17f..a28d11e 100644
--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -194,6 +194,7 @@
 	mm->mmap = NULL;
 	mm->mmap_cache = NULL;
 	mm->free_area_cache = oldmm->mmap_base;
+	mm->cached_hole_size = ~0UL;
 	mm->map_count = 0;
 	set_mm_counter(mm, rss, 0);
 	set_mm_counter(mm, anon_rss, 0);
@@ -249,8 +250,9 @@
 
 		/*
 		 * Link in the new vma and copy the page table entries:
-		 * link in first so that swapoff can see swap entries,
-		 * and try_to_unmap_one's find_vma find the new vma.
+		 * link in first so that swapoff can see swap entries.
+		 * Note that, exceptionally, here the vma is inserted
+		 * without holding mm->mmap_sem.
 		 */
 		spin_lock(&mm->page_table_lock);
 		*pprev = tmp;
@@ -322,6 +324,7 @@
 	mm->ioctx_list = NULL;
 	mm->default_kioctx = (struct kioctx)INIT_KIOCTX(mm->default_kioctx, *mm);
 	mm->free_area_cache = TASK_UNMAPPED_BASE;
+	mm->cached_hole_size = ~0UL;
 
 	if (likely(!mm_alloc_pgd(mm))) {
 		mm->def_flags = 0;
diff --git a/kernel/irq/manage.c b/kernel/irq/manage.c
index 5202e4c..ac67009 100644
--- a/kernel/irq/manage.c
+++ b/kernel/irq/manage.c
@@ -6,6 +6,7 @@
  * This file contains driver APIs to the irq subsystem.
  */
 
+#include <linux/config.h>
 #include <linux/irq.h>
 #include <linux/module.h>
 #include <linux/random.h>
@@ -255,6 +256,13 @@
 
 			/* Found it - now remove it from the list of entries */
 			*pp = action->next;
+
+			/* Currently used only by UML, might disappear one day.*/
+#ifdef CONFIG_IRQ_RELEASE_METHOD
+			if (desc->handler->release)
+				desc->handler->release(irq, dev_id);
+#endif
+
 			if (!desc->action) {
 				desc->status |= IRQ_DISABLED;
 				if (desc->handler->shutdown)
diff --git a/kernel/module.c b/kernel/module.c
index 83b3d37..a566745 100644
--- a/kernel/module.c
+++ b/kernel/module.c
@@ -379,7 +379,7 @@
 	for (i = 0; i < NR_CPUS; i++)
 		local_set(&mod->ref[i].count, 0);
 	/* Hold reference count during initialization. */
-	local_set(&mod->ref[_smp_processor_id()].count, 1);
+	local_set(&mod->ref[raw_smp_processor_id()].count, 1);
 	/* Backwards compatibility macros put refcount during init. */
 	mod->waiter = current;
 }
diff --git a/kernel/power/smp.c b/kernel/power/smp.c
index cba3584b..457c230 100644
--- a/kernel/power/smp.c
+++ b/kernel/power/smp.c
@@ -48,11 +48,11 @@
 {
 	oldmask = current->cpus_allowed;
 	set_cpus_allowed(current, cpumask_of_cpu(0));
-	printk("Freezing CPUs (at %d)", _smp_processor_id());
+	printk("Freezing CPUs (at %d)", raw_smp_processor_id());
 	current->state = TASK_INTERRUPTIBLE;
 	schedule_timeout(HZ);
 	printk("...");
-	BUG_ON(_smp_processor_id() != 0);
+	BUG_ON(raw_smp_processor_id() != 0);
 
 	/* FIXME: for this to work, all the CPUs must be running
 	 * "idle" thread (or we deadlock). Is that guaranteed? */
diff --git a/kernel/sched.c b/kernel/sched.c
index f12a0c8..deca041 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -3814,7 +3814,7 @@
  */
 void __sched io_schedule(void)
 {
-	struct runqueue *rq = &per_cpu(runqueues, _smp_processor_id());
+	struct runqueue *rq = &per_cpu(runqueues, raw_smp_processor_id());
 
 	atomic_inc(&rq->nr_iowait);
 	schedule();
@@ -3825,7 +3825,7 @@
 
 long __sched io_schedule_timeout(long timeout)
 {
-	struct runqueue *rq = &per_cpu(runqueues, _smp_processor_id());
+	struct runqueue *rq = &per_cpu(runqueues, raw_smp_processor_id());
 	long ret;
 
 	atomic_inc(&rq->nr_iowait);
diff --git a/kernel/stop_machine.c b/kernel/stop_machine.c
index 6116b25..84a9d18 100644
--- a/kernel/stop_machine.c
+++ b/kernel/stop_machine.c
@@ -100,7 +100,7 @@
 	stopmachine_state = STOPMACHINE_WAIT;
 
 	for_each_online_cpu(i) {
-		if (i == _smp_processor_id())
+		if (i == raw_smp_processor_id())
 			continue;
 		ret = kernel_thread(stopmachine, (void *)(long)i,CLONE_KERNEL);
 		if (ret < 0)
@@ -182,7 +182,7 @@
 
 	/* If they don't care which CPU fn runs on, bind to any online one. */
 	if (cpu == NR_CPUS)
-		cpu = _smp_processor_id();
+		cpu = raw_smp_processor_id();
 
 	p = kthread_create(do_stop, &smdata, "kstopmachine");
 	if (!IS_ERR(p)) {
diff --git a/kernel/sys_ni.c b/kernel/sys_ni.c
index 0dda70e..6f15bea 100644
--- a/kernel/sys_ni.c
+++ b/kernel/sys_ni.c
@@ -77,6 +77,7 @@
 cond_syscall(sys_keyctl);
 cond_syscall(compat_sys_keyctl);
 cond_syscall(compat_sys_socketcall);
+cond_syscall(sys_set_zone_reclaim);
 
 /* arch-specific weak syscall entries */
 cond_syscall(sys_pciconfig_read);
diff --git a/lib/Kconfig b/lib/Kconfig
index eeb4522..2d4d4e3 100644
--- a/lib/Kconfig
+++ b/lib/Kconfig
@@ -40,6 +40,12 @@
 	tristate
 
 #
+# Generic allocator support is selected if needed
+#
+config GENERIC_ALLOCATOR
+	boolean
+
+#
 # reed solomon support is select'ed if needed
 #
 config REED_SOLOMON
diff --git a/lib/Makefile b/lib/Makefile
index 9eccea9..dcb4231 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -20,6 +20,7 @@
 lib-$(CONFIG_RWSEM_XCHGADD_ALGORITHM) += rwsem.o
 lib-$(CONFIG_GENERIC_FIND_NEXT_BIT) += find_next_bit.o
 obj-$(CONFIG_LOCK_KERNEL) += kernel_lock.o
+obj-$(CONFIG_DEBUG_PREEMPT) += smp_processor_id.o
 
 ifneq ($(CONFIG_HAVE_DEC_LOCK),y) 
   lib-y += dec_and_lock.o
@@ -29,6 +30,7 @@
 obj-$(CONFIG_CRC32)	+= crc32.o
 obj-$(CONFIG_LIBCRC32C)	+= libcrc32c.o
 obj-$(CONFIG_GENERIC_IOMAP) += iomap.o
+obj-$(CONFIG_GENERIC_ALLOCATOR) += genalloc.o
 
 obj-$(CONFIG_ZLIB_INFLATE) += zlib_inflate/
 obj-$(CONFIG_ZLIB_DEFLATE) += zlib_deflate/
diff --git a/lib/genalloc.c b/lib/genalloc.c
new file mode 100644
index 0000000..d6d30d2e
--- /dev/null
+++ b/lib/genalloc.c
@@ -0,0 +1,188 @@
+/*
+ * Basic general purpose allocator for managing special purpose memory
+ * not managed by the regular kmalloc/kfree interface.
+ * Uses for this includes on-device special memory, uncached memory
+ * etc.
+ *
+ * This code is based on the buddy allocator found in the sym53c8xx_2
+ * driver Copyright (C) 1999-2001  Gerard Roudier <groudier@free.fr>,
+ * and adapted for general purpose use.
+ *
+ * Copyright 2005 (C) Jes Sorensen <jes@trained-monkey.org>
+ *
+ * This source code is licensed under the GNU General Public License,
+ * Version 2.  See the file COPYING for more details.
+ */
+
+#include <linux/module.h>
+#include <linux/stddef.h>
+#include <linux/kernel.h>
+#include <linux/string.h>
+#include <linux/slab.h>
+#include <linux/init.h>
+#include <linux/mm.h>
+#include <linux/spinlock.h>
+#include <linux/genalloc.h>
+
+#include <asm/page.h>
+
+
+struct gen_pool *gen_pool_create(int nr_chunks, int max_chunk_shift,
+				 unsigned long (*fp)(struct gen_pool *),
+				 unsigned long data)
+{
+	struct gen_pool *poolp;
+	unsigned long tmp;
+	int i;
+
+	/*
+	 * This is really an arbitrary limit, +10 is enough for
+	 * IA64_GRANULE_SHIFT, aka 16MB. If anyone needs a large limit
+	 * this can be increased without problems.
+	 */
+	if ((max_chunk_shift > (PAGE_SHIFT + 10)) ||
+	    ((max_chunk_shift < ALLOC_MIN_SHIFT) && max_chunk_shift))
+		return NULL;
+
+	if (!max_chunk_shift)
+		max_chunk_shift = PAGE_SHIFT;
+
+	poolp = kmalloc(sizeof(struct gen_pool), GFP_KERNEL);
+	if (!poolp)
+		return NULL;
+	memset(poolp, 0, sizeof(struct gen_pool));
+	poolp->h = kmalloc(sizeof(struct gen_pool_link) *
+			   (max_chunk_shift - ALLOC_MIN_SHIFT + 1),
+			   GFP_KERNEL);
+	if (!poolp->h) {
+		printk(KERN_WARNING "gen_pool_alloc() failed to allocate\n");
+		kfree(poolp);
+		return NULL;
+	}
+	memset(poolp->h, 0, sizeof(struct gen_pool_link) *
+	       (max_chunk_shift - ALLOC_MIN_SHIFT + 1));
+
+	spin_lock_init(&poolp->lock);
+	poolp->get_new_chunk = fp;
+	poolp->max_chunk_shift = max_chunk_shift;
+	poolp->private = data;
+
+	for (i = 0; i < nr_chunks; i++) {
+		tmp = poolp->get_new_chunk(poolp);
+		printk(KERN_INFO "allocated %lx\n", tmp);
+		if (!tmp)
+			break;
+		gen_pool_free(poolp, tmp, (1 << poolp->max_chunk_shift));
+	}
+
+	return poolp;
+}
+EXPORT_SYMBOL(gen_pool_create);
+
+
+/*
+ *  Simple power of two buddy-like generic allocator.
+ *  Provides naturally aligned memory chunks.
+ */
+unsigned long gen_pool_alloc(struct gen_pool *poolp, int size)
+{
+	int j, i, s, max_chunk_size;
+	unsigned long a, flags;
+	struct gen_pool_link *h = poolp->h;
+
+	max_chunk_size = 1 << poolp->max_chunk_shift;
+
+	if (size > max_chunk_size)
+		return 0;
+
+	i = 0;
+
+	size = max(size, 1 << ALLOC_MIN_SHIFT);
+	s = roundup_pow_of_two(size);
+
+	j = i;
+
+	spin_lock_irqsave(&poolp->lock, flags);
+	while (!h[j].next) {
+		if (s == max_chunk_size) {
+			struct gen_pool_link *ptr;
+			spin_unlock_irqrestore(&poolp->lock, flags);
+			ptr = (struct gen_pool_link *)poolp->get_new_chunk(poolp);
+			spin_lock_irqsave(&poolp->lock, flags);
+			h[j].next = ptr;
+			if (h[j].next)
+				h[j].next->next = NULL;
+			break;
+		}
+		j++;
+		s <<= 1;
+	}
+	a = (unsigned long) h[j].next;
+	if (a) {
+		h[j].next = h[j].next->next;
+		/*
+		 * This should be split into a seperate function doing
+		 * the chunk split in order to support custom
+		 * handling memory not physically accessible by host
+		 */
+		while (j > i) {
+			j -= 1;
+			s >>= 1;
+			h[j].next = (struct gen_pool_link *) (a + s);
+			h[j].next->next = NULL;
+		}
+	}
+	spin_unlock_irqrestore(&poolp->lock, flags);
+	return a;
+}
+EXPORT_SYMBOL(gen_pool_alloc);
+
+
+/*
+ *  Counter-part of the generic allocator.
+ */
+void gen_pool_free(struct gen_pool *poolp, unsigned long ptr, int size)
+{
+	struct gen_pool_link *q;
+	struct gen_pool_link *h = poolp->h;
+	unsigned long a, b, flags;
+	int i, s, max_chunk_size;
+
+	max_chunk_size = 1 << poolp->max_chunk_shift;
+
+	if (size > max_chunk_size)
+		return;
+
+	i = 0;
+
+	size = max(size, 1 << ALLOC_MIN_SHIFT);
+	s = roundup_pow_of_two(size);
+
+	a = ptr;
+
+	spin_lock_irqsave(&poolp->lock, flags);
+	while (1) {
+		if (s == max_chunk_size) {
+			((struct gen_pool_link *)a)->next = h[i].next;
+			h[i].next = (struct gen_pool_link *)a;
+			break;
+		}
+		b = a ^ s;
+		q = &h[i];
+
+		while (q->next && q->next != (struct gen_pool_link *)b)
+			q = q->next;
+
+		if (!q->next) {
+			((struct gen_pool_link *)a)->next = h[i].next;
+			h[i].next = (struct gen_pool_link *)a;
+			break;
+		}
+		q->next = q->next->next;
+		a = a & b;
+		s <<= 1;
+		i++;
+	}
+	spin_unlock_irqrestore(&poolp->lock, flags);
+}
+EXPORT_SYMBOL(gen_pool_free);
diff --git a/lib/idr.c b/lib/idr.c
index 81fc430..c5be889 100644
--- a/lib/idr.c
+++ b/lib/idr.c
@@ -175,7 +175,7 @@
 	 * Add a new layer to the top of the tree if the requested
 	 * id is larger than the currently allocated space.
 	 */
-	while ((layers < MAX_LEVEL) && (id >= (1 << (layers*IDR_BITS)))) {
+	while ((layers < (MAX_LEVEL - 1)) && (id >= (1 << (layers*IDR_BITS)))) {
 		layers++;
 		if (!p->count)
 			continue;
diff --git a/lib/kernel_lock.c b/lib/kernel_lock.c
index 99b0ae3..bd2bc5d 100644
--- a/lib/kernel_lock.c
+++ b/lib/kernel_lock.c
@@ -9,61 +9,6 @@
 #include <linux/module.h>
 #include <linux/kallsyms.h>
 
-#if defined(CONFIG_PREEMPT) && defined(__smp_processor_id) && \
-		defined(CONFIG_DEBUG_PREEMPT)
-
-/*
- * Debugging check.
- */
-unsigned int smp_processor_id(void)
-{
-	unsigned long preempt_count = preempt_count();
-	int this_cpu = __smp_processor_id();
-	cpumask_t this_mask;
-
-	if (likely(preempt_count))
-		goto out;
-
-	if (irqs_disabled())
-		goto out;
-
-	/*
-	 * Kernel threads bound to a single CPU can safely use
-	 * smp_processor_id():
-	 */
-	this_mask = cpumask_of_cpu(this_cpu);
-
-	if (cpus_equal(current->cpus_allowed, this_mask))
-		goto out;
-
-	/*
-	 * It is valid to assume CPU-locality during early bootup:
-	 */
-	if (system_state != SYSTEM_RUNNING)
-		goto out;
-
-	/*
-	 * Avoid recursion:
-	 */
-	preempt_disable();
-
-	if (!printk_ratelimit())
-		goto out_enable;
-
-	printk(KERN_ERR "BUG: using smp_processor_id() in preemptible [%08x] code: %s/%d\n", preempt_count(), current->comm, current->pid);
-	print_symbol("caller is %s\n", (long)__builtin_return_address(0));
-	dump_stack();
-
-out_enable:
-	preempt_enable_no_resched();
-out:
-	return this_cpu;
-}
-
-EXPORT_SYMBOL(smp_processor_id);
-
-#endif /* PREEMPT && __smp_processor_id && DEBUG_PREEMPT */
-
 #ifdef CONFIG_PREEMPT_BKL
 /*
  * The 'big kernel semaphore'
diff --git a/lib/smp_processor_id.c b/lib/smp_processor_id.c
new file mode 100644
index 0000000..42c08ef
--- /dev/null
+++ b/lib/smp_processor_id.c
@@ -0,0 +1,55 @@
+/*
+ * lib/smp_processor_id.c
+ *
+ * DEBUG_PREEMPT variant of smp_processor_id().
+ */
+#include <linux/module.h>
+#include <linux/kallsyms.h>
+
+unsigned int debug_smp_processor_id(void)
+{
+	unsigned long preempt_count = preempt_count();
+	int this_cpu = raw_smp_processor_id();
+	cpumask_t this_mask;
+
+	if (likely(preempt_count))
+		goto out;
+
+	if (irqs_disabled())
+		goto out;
+
+	/*
+	 * Kernel threads bound to a single CPU can safely use
+	 * smp_processor_id():
+	 */
+	this_mask = cpumask_of_cpu(this_cpu);
+
+	if (cpus_equal(current->cpus_allowed, this_mask))
+		goto out;
+
+	/*
+	 * It is valid to assume CPU-locality during early bootup:
+	 */
+	if (system_state != SYSTEM_RUNNING)
+		goto out;
+
+	/*
+	 * Avoid recursion:
+	 */
+	preempt_disable();
+
+	if (!printk_ratelimit())
+		goto out_enable;
+
+	printk(KERN_ERR "BUG: using smp_processor_id() in preemptible [%08x] code: %s/%d\n", preempt_count(), current->comm, current->pid);
+	print_symbol("caller is %s\n", (long)__builtin_return_address(0));
+	dump_stack();
+
+out_enable:
+	preempt_enable_no_resched();
+out:
+	return this_cpu;
+}
+
+EXPORT_SYMBOL(debug_smp_processor_id);
+
diff --git a/mm/hugetlb.c b/mm/hugetlb.c
index 4eb5ae3..fbd1111 100644
--- a/mm/hugetlb.c
+++ b/mm/hugetlb.c
@@ -7,10 +7,14 @@
 #include <linux/init.h>
 #include <linux/module.h>
 #include <linux/mm.h>
-#include <linux/hugetlb.h>
 #include <linux/sysctl.h>
 #include <linux/highmem.h>
 #include <linux/nodemask.h>
+#include <linux/pagemap.h>
+#include <asm/page.h>
+#include <asm/pgtable.h>
+
+#include <linux/hugetlb.h>
 
 const unsigned long hugetlb_zero = 0, hugetlb_infinity = ~0UL;
 static unsigned long nr_huge_pages, free_huge_pages;
@@ -249,6 +253,72 @@
 	.nopage = hugetlb_nopage,
 };
 
+static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page)
+{
+	pte_t entry;
+
+	if (vma->vm_flags & VM_WRITE) {
+		entry =
+		    pte_mkwrite(pte_mkdirty(mk_pte(page, vma->vm_page_prot)));
+	} else {
+		entry = pte_wrprotect(mk_pte(page, vma->vm_page_prot));
+	}
+	entry = pte_mkyoung(entry);
+	entry = pte_mkhuge(entry);
+
+	return entry;
+}
+
+int copy_hugetlb_page_range(struct mm_struct *dst, struct mm_struct *src,
+			    struct vm_area_struct *vma)
+{
+	pte_t *src_pte, *dst_pte, entry;
+	struct page *ptepage;
+	unsigned long addr = vma->vm_start;
+	unsigned long end = vma->vm_end;
+
+	while (addr < end) {
+		dst_pte = huge_pte_alloc(dst, addr);
+		if (!dst_pte)
+			goto nomem;
+		src_pte = huge_pte_offset(src, addr);
+		BUG_ON(!src_pte || pte_none(*src_pte)); /* prefaulted */
+		entry = *src_pte;
+		ptepage = pte_page(entry);
+		get_page(ptepage);
+		add_mm_counter(dst, rss, HPAGE_SIZE / PAGE_SIZE);
+		set_huge_pte_at(dst, addr, dst_pte, entry);
+		addr += HPAGE_SIZE;
+	}
+	return 0;
+
+nomem:
+	return -ENOMEM;
+}
+
+void unmap_hugepage_range(struct vm_area_struct *vma, unsigned long start,
+			  unsigned long end)
+{
+	struct mm_struct *mm = vma->vm_mm;
+	unsigned long address;
+	pte_t pte;
+	struct page *page;
+
+	WARN_ON(!is_vm_hugetlb_page(vma));
+	BUG_ON(start & ~HPAGE_MASK);
+	BUG_ON(end & ~HPAGE_MASK);
+
+	for (address = start; address < end; address += HPAGE_SIZE) {
+		pte = huge_ptep_get_and_clear(mm, address, huge_pte_offset(mm, address));
+		if (pte_none(pte))
+			continue;
+		page = pte_page(pte);
+		put_page(page);
+	}
+	add_mm_counter(mm, rss,  -((end - start) >> PAGE_SHIFT));
+	flush_tlb_range(vma, start, end);
+}
+
 void zap_hugepage_range(struct vm_area_struct *vma,
 			unsigned long start, unsigned long length)
 {
@@ -258,3 +328,108 @@
 	unmap_hugepage_range(vma, start, start + length);
 	spin_unlock(&mm->page_table_lock);
 }
+
+int hugetlb_prefault(struct address_space *mapping, struct vm_area_struct *vma)
+{
+	struct mm_struct *mm = current->mm;
+	unsigned long addr;
+	int ret = 0;
+
+	WARN_ON(!is_vm_hugetlb_page(vma));
+	BUG_ON(vma->vm_start & ~HPAGE_MASK);
+	BUG_ON(vma->vm_end & ~HPAGE_MASK);
+
+	hugetlb_prefault_arch_hook(mm);
+
+	spin_lock(&mm->page_table_lock);
+	for (addr = vma->vm_start; addr < vma->vm_end; addr += HPAGE_SIZE) {
+		unsigned long idx;
+		pte_t *pte = huge_pte_alloc(mm, addr);
+		struct page *page;
+
+		if (!pte) {
+			ret = -ENOMEM;
+			goto out;
+		}
+		if (! pte_none(*pte))
+			hugetlb_clean_stale_pgtable(pte);
+
+		idx = ((addr - vma->vm_start) >> HPAGE_SHIFT)
+			+ (vma->vm_pgoff >> (HPAGE_SHIFT - PAGE_SHIFT));
+		page = find_get_page(mapping, idx);
+		if (!page) {
+			/* charge the fs quota first */
+			if (hugetlb_get_quota(mapping)) {
+				ret = -ENOMEM;
+				goto out;
+			}
+			page = alloc_huge_page();
+			if (!page) {
+				hugetlb_put_quota(mapping);
+				ret = -ENOMEM;
+				goto out;
+			}
+			ret = add_to_page_cache(page, mapping, idx, GFP_ATOMIC);
+			if (! ret) {
+				unlock_page(page);
+			} else {
+				hugetlb_put_quota(mapping);
+				free_huge_page(page);
+				goto out;
+			}
+		}
+		add_mm_counter(mm, rss, HPAGE_SIZE / PAGE_SIZE);
+		set_huge_pte_at(mm, addr, pte, make_huge_pte(vma, page));
+	}
+out:
+	spin_unlock(&mm->page_table_lock);
+	return ret;
+}
+
+int follow_hugetlb_page(struct mm_struct *mm, struct vm_area_struct *vma,
+			struct page **pages, struct vm_area_struct **vmas,
+			unsigned long *position, int *length, int i)
+{
+	unsigned long vpfn, vaddr = *position;
+	int remainder = *length;
+
+	BUG_ON(!is_vm_hugetlb_page(vma));
+
+	vpfn = vaddr/PAGE_SIZE;
+	while (vaddr < vma->vm_end && remainder) {
+
+		if (pages) {
+			pte_t *pte;
+			struct page *page;
+
+			/* Some archs (sparc64, sh*) have multiple
+			 * pte_ts to each hugepage.  We have to make
+			 * sure we get the first, for the page
+			 * indexing below to work. */
+			pte = huge_pte_offset(mm, vaddr & HPAGE_MASK);
+
+			/* hugetlb should be locked, and hence, prefaulted */
+			WARN_ON(!pte || pte_none(*pte));
+
+			page = &pte_page(*pte)[vpfn % (HPAGE_SIZE/PAGE_SIZE)];
+
+			WARN_ON(!PageCompound(page));
+
+			get_page(page);
+			pages[i] = page;
+		}
+
+		if (vmas)
+			vmas[i] = vma;
+
+		vaddr += PAGE_SIZE;
+		++vpfn;
+		--remainder;
+		++i;
+	}
+
+	*length = remainder;
+	*position = vaddr;
+
+	return i;
+}
diff --git a/mm/madvise.c b/mm/madvise.c
index 944b5e5..e310805 100644
--- a/mm/madvise.c
+++ b/mm/madvise.c
@@ -8,17 +8,47 @@
 #include <linux/mman.h>
 #include <linux/pagemap.h>
 #include <linux/syscalls.h>
+#include <linux/mempolicy.h>
 #include <linux/hugetlb.h>
 
 /*
  * We can potentially split a vm area into separate
  * areas, each area with its own behavior.
  */
-static long madvise_behavior(struct vm_area_struct * vma, unsigned long start,
-			     unsigned long end, int behavior)
+static long madvise_behavior(struct vm_area_struct * vma,
+		     struct vm_area_struct **prev,
+		     unsigned long start, unsigned long end, int behavior)
 {
 	struct mm_struct * mm = vma->vm_mm;
 	int error = 0;
+	pgoff_t pgoff;
+	int new_flags = vma->vm_flags & ~VM_READHINTMASK;
+
+	switch (behavior) {
+	case MADV_SEQUENTIAL:
+		new_flags |= VM_SEQ_READ;
+		break;
+	case MADV_RANDOM:
+		new_flags |= VM_RAND_READ;
+		break;
+	default:
+		break;
+	}
+
+	if (new_flags == vma->vm_flags) {
+		*prev = vma;
+		goto success;
+	}
+
+	pgoff = vma->vm_pgoff + ((start - vma->vm_start) >> PAGE_SHIFT);
+	*prev = vma_merge(mm, *prev, start, end, new_flags, vma->anon_vma,
+				vma->vm_file, pgoff, vma_policy(vma));
+	if (*prev) {
+		vma = *prev;
+		goto success;
+	}
+
+	*prev = vma;
 
 	if (start != vma->vm_start) {
 		error = split_vma(mm, vma, start, 1);
@@ -36,21 +66,12 @@
 	 * vm_flags is protected by the mmap_sem held in write mode.
 	 */
 	VM_ClearReadHint(vma);
-
-	switch (behavior) {
-	case MADV_SEQUENTIAL:
-		vma->vm_flags |= VM_SEQ_READ;
-		break;
-	case MADV_RANDOM:
-		vma->vm_flags |= VM_RAND_READ;
-		break;
-	default:
-		break;
-	}
+	vma->vm_flags = new_flags;
 
 out:
 	if (error == -ENOMEM)
 		error = -EAGAIN;
+success:
 	return error;
 }
 
@@ -58,6 +79,7 @@
  * Schedule all required I/O operations.  Do not wait for completion.
  */
 static long madvise_willneed(struct vm_area_struct * vma,
+			     struct vm_area_struct ** prev,
 			     unsigned long start, unsigned long end)
 {
 	struct file *file = vma->vm_file;
@@ -65,6 +87,7 @@
 	if (!file)
 		return -EBADF;
 
+	*prev = vma;
 	start = ((start - vma->vm_start) >> PAGE_SHIFT) + vma->vm_pgoff;
 	if (end > vma->vm_end)
 		end = vma->vm_end;
@@ -95,8 +118,10 @@
  * dirty pages is already available as msync(MS_INVALIDATE).
  */
 static long madvise_dontneed(struct vm_area_struct * vma,
+			     struct vm_area_struct ** prev,
 			     unsigned long start, unsigned long end)
 {
+	*prev = vma;
 	if ((vma->vm_flags & VM_LOCKED) || is_vm_hugetlb_page(vma))
 		return -EINVAL;
 
@@ -111,8 +136,8 @@
 	return 0;
 }
 
-static long madvise_vma(struct vm_area_struct * vma, unsigned long start,
-			unsigned long end, int behavior)
+static long madvise_vma(struct vm_area_struct *vma, struct vm_area_struct **prev,
+			unsigned long start, unsigned long end, int behavior)
 {
 	long error = -EBADF;
 
@@ -120,15 +145,15 @@
 	case MADV_NORMAL:
 	case MADV_SEQUENTIAL:
 	case MADV_RANDOM:
-		error = madvise_behavior(vma, start, end, behavior);
+		error = madvise_behavior(vma, prev, start, end, behavior);
 		break;
 
 	case MADV_WILLNEED:
-		error = madvise_willneed(vma, start, end);
+		error = madvise_willneed(vma, prev, start, end);
 		break;
 
 	case MADV_DONTNEED:
-		error = madvise_dontneed(vma, start, end);
+		error = madvise_dontneed(vma, prev, start, end);
 		break;
 
 	default:
@@ -175,8 +200,8 @@
  */
 asmlinkage long sys_madvise(unsigned long start, size_t len_in, int behavior)
 {
-	unsigned long end;
-	struct vm_area_struct * vma;
+	unsigned long end, tmp;
+	struct vm_area_struct * vma, *prev;
 	int unmapped_error = 0;
 	int error = -EINVAL;
 	size_t len;
@@ -202,40 +227,42 @@
 	/*
 	 * If the interval [start,end) covers some unmapped address
 	 * ranges, just ignore them, but return -ENOMEM at the end.
+	 * - different from the way of handling in mlock etc.
 	 */
-	vma = find_vma(current->mm, start);
+	vma = find_vma_prev(current->mm, start, &prev);
+	if (!vma && prev)
+		vma = prev->vm_next;
 	for (;;) {
 		/* Still start < end. */
 		error = -ENOMEM;
 		if (!vma)
 			goto out;
 
-		/* Here start < vma->vm_end. */
+		/* Here start < (end|vma->vm_end). */
 		if (start < vma->vm_start) {
 			unmapped_error = -ENOMEM;
 			start = vma->vm_start;
+			if (start >= end)
+				goto out;
 		}
 
-		/* Here vma->vm_start <= start < vma->vm_end. */
-		if (end <= vma->vm_end) {
-			if (start < end) {
-				error = madvise_vma(vma, start, end,
-							behavior);
-				if (error)
-					goto out;
-			}
-			error = unmapped_error;
-			goto out;
-		}
+		/* Here vma->vm_start <= start < (end|vma->vm_end) */
+		tmp = vma->vm_end;
+		if (end < tmp)
+			tmp = end;
 
-		/* Here vma->vm_start <= start < vma->vm_end < end. */
-		error = madvise_vma(vma, start, vma->vm_end, behavior);
+		/* Here vma->vm_start <= start < tmp <= (end|vma->vm_end). */
+		error = madvise_vma(vma, &prev, start, tmp, behavior);
 		if (error)
 			goto out;
-		start = vma->vm_end;
-		vma = vma->vm_next;
+		start = tmp;
+		if (start < prev->vm_end)
+			start = prev->vm_end;
+		error = unmapped_error;
+		if (start >= end)
+			goto out;
+		vma = prev->vm_next;
 	}
-
 out:
 	up_write(&current->mm->mmap_sem);
 	return error;
diff --git a/mm/memory.c b/mm/memory.c
index d209f74..da91b7b 100644
--- a/mm/memory.c
+++ b/mm/memory.c
@@ -840,23 +840,8 @@
 {
 	return __follow_page(mm, address, /*read*/1, /*write*/0) != NULL;
 }
-
 EXPORT_SYMBOL(check_user_page_readable);
 
-/* 
- * Given a physical address, is there a useful struct page pointing to
- * it?  This may become more complex in the future if we start dealing
- * with IO-aperture pages for direct-IO.
- */
-
-static inline struct page *get_page_map(struct page *page)
-{
-	if (!pfn_valid(page_to_pfn(page)))
-		return NULL;
-	return page;
-}
-
-
 static inline int
 untouched_anonymous_page(struct mm_struct* mm, struct vm_area_struct *vma,
 			 unsigned long address)
@@ -887,7 +872,6 @@
 	return 0;
 }
 
-
 int get_user_pages(struct task_struct *tsk, struct mm_struct *mm,
 		unsigned long start, int len, int write, int force,
 		struct page **pages, struct vm_area_struct **vmas)
@@ -951,21 +935,21 @@
 		}
 		spin_lock(&mm->page_table_lock);
 		do {
-			struct page *map;
+			struct page *page;
 			int lookup_write = write;
 
 			cond_resched_lock(&mm->page_table_lock);
-			while (!(map = follow_page(mm, start, lookup_write))) {
+			while (!(page = follow_page(mm, start, lookup_write))) {
 				/*
 				 * Shortcut for anonymous pages. We don't want
 				 * to force the creation of pages tables for
-				 * insanly big anonymously mapped areas that
+				 * insanely big anonymously mapped areas that
 				 * nobody touched so far. This is important
 				 * for doing a core dump for these mappings.
 				 */
 				if (!lookup_write &&
 				    untouched_anonymous_page(mm,vma,start)) {
-					map = ZERO_PAGE(start);
+					page = ZERO_PAGE(start);
 					break;
 				}
 				spin_unlock(&mm->page_table_lock);
@@ -994,30 +978,21 @@
 				spin_lock(&mm->page_table_lock);
 			}
 			if (pages) {
-				pages[i] = get_page_map(map);
-				if (!pages[i]) {
-					spin_unlock(&mm->page_table_lock);
-					while (i--)
-						page_cache_release(pages[i]);
-					i = -EFAULT;
-					goto out;
-				}
-				flush_dcache_page(pages[i]);
-				if (!PageReserved(pages[i]))
-					page_cache_get(pages[i]);
+				pages[i] = page;
+				flush_dcache_page(page);
+				if (!PageReserved(page))
+					page_cache_get(page);
 			}
 			if (vmas)
 				vmas[i] = vma;
 			i++;
 			start += PAGE_SIZE;
 			len--;
-		} while(len && start < vma->vm_end);
+		} while (len && start < vma->vm_end);
 		spin_unlock(&mm->page_table_lock);
-	} while(len);
-out:
+	} while (len);
 	return i;
 }
-
 EXPORT_SYMBOL(get_user_pages);
 
 static int zeromap_pte_range(struct mm_struct *mm, pmd_t *pmd,
@@ -1264,7 +1239,7 @@
 	}
 	old_page = pfn_to_page(pfn);
 
-	if (!TestSetPageLocked(old_page)) {
+	if (PageAnon(old_page) && !TestSetPageLocked(old_page)) {
 		int reuse = can_share_swap_page(old_page);
 		unlock_page(old_page);
 		if (reuse) {
@@ -1711,10 +1686,6 @@
 	}
 
 	/* The page isn't present yet, go ahead with the fault. */
-		
-	swap_free(entry);
-	if (vm_swap_full())
-		remove_exclusive_swap_page(page);
 
 	inc_mm_counter(mm, rss);
 	pte = mk_pte(page, vma->vm_page_prot);
@@ -1722,12 +1693,16 @@
 		pte = maybe_mkwrite(pte_mkdirty(pte), vma);
 		write_access = 0;
 	}
-	unlock_page(page);
 
 	flush_icache_page(vma, page);
 	set_pte_at(mm, address, page_table, pte);
 	page_add_anon_rmap(page, vma, address);
 
+	swap_free(entry);
+	if (vm_swap_full())
+		remove_exclusive_swap_page(page);
+	unlock_page(page);
+
 	if (write_access) {
 		if (do_wp_page(mm, vma, address,
 				page_table, pmd, pte) == VM_FAULT_OOM)
diff --git a/mm/mempolicy.c b/mm/mempolicy.c
index 08c41da..cb41c31 100644
--- a/mm/mempolicy.c
+++ b/mm/mempolicy.c
@@ -238,46 +238,80 @@
 }
 
 /* Ensure all existing pages follow the policy. */
-static int
-verify_pages(struct mm_struct *mm,
-	     unsigned long addr, unsigned long end, unsigned long *nodes)
+static int check_pte_range(struct mm_struct *mm, pmd_t *pmd,
+		unsigned long addr, unsigned long end, unsigned long *nodes)
 {
-	while (addr < end) {
-		struct page *p;
-		pte_t *pte;
-		pmd_t *pmd;
-		pud_t *pud;
-		pgd_t *pgd;
-		pgd = pgd_offset(mm, addr);
-		if (pgd_none(*pgd)) {
-			unsigned long next = (addr + PGDIR_SIZE) & PGDIR_MASK;
-			if (next > addr)
-				break;
-			addr = next;
+	pte_t *orig_pte;
+	pte_t *pte;
+
+	spin_lock(&mm->page_table_lock);
+	orig_pte = pte = pte_offset_map(pmd, addr);
+	do {
+		unsigned long pfn;
+		unsigned int nid;
+
+		if (!pte_present(*pte))
 			continue;
-		}
-		pud = pud_offset(pgd, addr);
-		if (pud_none(*pud)) {
-			addr = (addr + PUD_SIZE) & PUD_MASK;
+		pfn = pte_pfn(*pte);
+		if (!pfn_valid(pfn))
 			continue;
-		}
-		pmd = pmd_offset(pud, addr);
-		if (pmd_none(*pmd)) {
-			addr = (addr + PMD_SIZE) & PMD_MASK;
+		nid = pfn_to_nid(pfn);
+		if (!test_bit(nid, nodes))
+			break;
+	} while (pte++, addr += PAGE_SIZE, addr != end);
+	pte_unmap(orig_pte);
+	spin_unlock(&mm->page_table_lock);
+	return addr != end;
+}
+
+static inline int check_pmd_range(struct mm_struct *mm, pud_t *pud,
+		unsigned long addr, unsigned long end, unsigned long *nodes)
+{
+	pmd_t *pmd;
+	unsigned long next;
+
+	pmd = pmd_offset(pud, addr);
+	do {
+		next = pmd_addr_end(addr, end);
+		if (pmd_none_or_clear_bad(pmd))
 			continue;
-		}
-		p = NULL;
-		pte = pte_offset_map(pmd, addr);
-		if (pte_present(*pte))
-			p = pte_page(*pte);
-		pte_unmap(pte);
-		if (p) {
-			unsigned nid = page_to_nid(p);
-			if (!test_bit(nid, nodes))
-				return -EIO;
-		}
-		addr += PAGE_SIZE;
-	}
+		if (check_pte_range(mm, pmd, addr, next, nodes))
+			return -EIO;
+	} while (pmd++, addr = next, addr != end);
+	return 0;
+}
+
+static inline int check_pud_range(struct mm_struct *mm, pgd_t *pgd,
+		unsigned long addr, unsigned long end, unsigned long *nodes)
+{
+	pud_t *pud;
+	unsigned long next;
+
+	pud = pud_offset(pgd, addr);
+	do {
+		next = pud_addr_end(addr, end);
+		if (pud_none_or_clear_bad(pud))
+			continue;
+		if (check_pmd_range(mm, pud, addr, next, nodes))
+			return -EIO;
+	} while (pud++, addr = next, addr != end);
+	return 0;
+}
+
+static inline int check_pgd_range(struct mm_struct *mm,
+		unsigned long addr, unsigned long end, unsigned long *nodes)
+{
+	pgd_t *pgd;
+	unsigned long next;
+
+	pgd = pgd_offset(mm, addr);
+	do {
+		next = pgd_addr_end(addr, end);
+		if (pgd_none_or_clear_bad(pgd))
+			continue;
+		if (check_pud_range(mm, pgd, addr, next, nodes))
+			return -EIO;
+	} while (pgd++, addr = next, addr != end);
 	return 0;
 }
 
@@ -299,7 +333,7 @@
 		if (prev && prev->vm_end < vma->vm_start)
 			return ERR_PTR(-EFAULT);
 		if ((flags & MPOL_MF_STRICT) && !is_vm_hugetlb_page(vma)) {
-			err = verify_pages(vma->vm_mm,
+			err = check_pgd_range(vma->vm_mm,
 					   vma->vm_start, vma->vm_end, nodes);
 			if (err) {
 				first = ERR_PTR(err);
@@ -721,7 +755,7 @@
 	zl = NODE_DATA(nid)->node_zonelists + (gfp & GFP_ZONEMASK);
 	page = __alloc_pages(gfp, order, zl);
 	if (page && page_zone(page) == zl->zones[0]) {
-		zl->zones[0]->pageset[get_cpu()].interleave_hit++;
+		zone_pcp(zl->zones[0],get_cpu())->interleave_hit++;
 		put_cpu();
 	}
 	return page;
diff --git a/mm/mmap.c b/mm/mmap.c
index de54acd..da3fa90 100644
--- a/mm/mmap.c
+++ b/mm/mmap.c
@@ -1175,7 +1175,12 @@
 		    (!vma || addr + len <= vma->vm_start))
 			return addr;
 	}
-	start_addr = addr = mm->free_area_cache;
+	if (len > mm->cached_hole_size) {
+	        start_addr = addr = mm->free_area_cache;
+	} else {
+	        start_addr = addr = TASK_UNMAPPED_BASE;
+	        mm->cached_hole_size = 0;
+	}
 
 full_search:
 	for (vma = find_vma(mm, addr); ; vma = vma->vm_next) {
@@ -1186,7 +1191,9 @@
 			 * some holes.
 			 */
 			if (start_addr != TASK_UNMAPPED_BASE) {
-				start_addr = addr = TASK_UNMAPPED_BASE;
+				addr = TASK_UNMAPPED_BASE;
+			        start_addr = addr;
+				mm->cached_hole_size = 0;
 				goto full_search;
 			}
 			return -ENOMEM;
@@ -1198,19 +1205,22 @@
 			mm->free_area_cache = addr + len;
 			return addr;
 		}
+		if (addr + mm->cached_hole_size < vma->vm_start)
+		        mm->cached_hole_size = vma->vm_start - addr;
 		addr = vma->vm_end;
 	}
 }
 #endif	
 
-void arch_unmap_area(struct vm_area_struct *area)
+void arch_unmap_area(struct mm_struct *mm, unsigned long addr)
 {
 	/*
 	 * Is this a new hole at the lowest possible address?
 	 */
-	if (area->vm_start >= TASK_UNMAPPED_BASE &&
-			area->vm_start < area->vm_mm->free_area_cache)
-		area->vm_mm->free_area_cache = area->vm_start;
+	if (addr >= TASK_UNMAPPED_BASE && addr < mm->free_area_cache) {
+		mm->free_area_cache = addr;
+		mm->cached_hole_size = ~0UL;
+	}
 }
 
 /*
@@ -1240,6 +1250,12 @@
 			return addr;
 	}
 
+	/* check if free_area_cache is useful for us */
+	if (len <= mm->cached_hole_size) {
+ 	        mm->cached_hole_size = 0;
+ 		mm->free_area_cache = mm->mmap_base;
+ 	}
+
 	/* either no address requested or can't fit in requested address hole */
 	addr = mm->free_area_cache;
 
@@ -1251,6 +1267,9 @@
 			return (mm->free_area_cache = addr-len);
 	}
 
+	if (mm->mmap_base < len)
+		goto bottomup;
+
 	addr = mm->mmap_base-len;
 
 	do {
@@ -1264,38 +1283,45 @@
 			/* remember the address as a hint for next time */
 			return (mm->free_area_cache = addr);
 
+ 		/* remember the largest hole we saw so far */
+ 		if (addr + mm->cached_hole_size < vma->vm_start)
+ 		        mm->cached_hole_size = vma->vm_start - addr;
+
 		/* try just below the current vma->vm_start */
 		addr = vma->vm_start-len;
 	} while (len < vma->vm_start);
 
+bottomup:
 	/*
 	 * A failed mmap() very likely causes application failure,
 	 * so fall back to the bottom-up function here. This scenario
 	 * can happen with large stack limits and large mmap()
 	 * allocations.
 	 */
-	mm->free_area_cache = TASK_UNMAPPED_BASE;
+	mm->cached_hole_size = ~0UL;
+  	mm->free_area_cache = TASK_UNMAPPED_BASE;
 	addr = arch_get_unmapped_area(filp, addr0, len, pgoff, flags);
 	/*
 	 * Restore the topdown base:
 	 */
 	mm->free_area_cache = mm->mmap_base;
+	mm->cached_hole_size = ~0UL;
 
 	return addr;
 }
 #endif
 
-void arch_unmap_area_topdown(struct vm_area_struct *area)
+void arch_unmap_area_topdown(struct mm_struct *mm, unsigned long addr)
 {
 	/*
 	 * Is this a new hole at the highest possible address?
 	 */
-	if (area->vm_end > area->vm_mm->free_area_cache)
-		area->vm_mm->free_area_cache = area->vm_end;
+	if (addr > mm->free_area_cache)
+		mm->free_area_cache = addr;
 
 	/* dont allow allocations above current base */
-	if (area->vm_mm->free_area_cache > area->vm_mm->mmap_base)
-		area->vm_mm->free_area_cache = area->vm_mm->mmap_base;
+	if (mm->free_area_cache > mm->mmap_base)
+		mm->free_area_cache = mm->mmap_base;
 }
 
 unsigned long
@@ -1595,7 +1621,6 @@
 	if (area->vm_flags & VM_LOCKED)
 		area->vm_mm->locked_vm -= len >> PAGE_SHIFT;
 	vm_stat_unaccount(area);
-	area->vm_mm->unmap_area(area);
 	remove_vm_struct(area);
 }
 
@@ -1649,6 +1674,7 @@
 {
 	struct vm_area_struct **insertion_point;
 	struct vm_area_struct *tail_vma = NULL;
+	unsigned long addr;
 
 	insertion_point = (prev ? &prev->vm_next : &mm->mmap);
 	do {
@@ -1659,6 +1685,11 @@
 	} while (vma && vma->vm_start < end);
 	*insertion_point = vma;
 	tail_vma->vm_next = NULL;
+	if (mm->unmap_area == arch_unmap_area)
+		addr = prev ? prev->vm_end : mm->mmap_base;
+	else
+		addr = vma ?  vma->vm_start : mm->mmap_base;
+	mm->unmap_area(mm, addr);
 	mm->mmap_cache = NULL;		/* Kill the cache. */
 }
 
diff --git a/mm/msync.c b/mm/msync.c
index 090f426..d0f5a1b 100644
--- a/mm/msync.c
+++ b/mm/msync.c
@@ -34,6 +34,8 @@
 
 		if (!pte_present(*pte))
 			continue;
+		if (!pte_maybe_dirty(*pte))
+			continue;
 		pfn = pte_pfn(*pte);
 		if (!pfn_valid(pfn))
 			continue;
diff --git a/mm/nommu.c b/mm/nommu.c
index c53e9c8..ce74452 100644
--- a/mm/nommu.c
+++ b/mm/nommu.c
@@ -1067,7 +1067,7 @@
 	return -ENOMEM;
 }
 
-void arch_unmap_area(struct vm_area_struct *area)
+void arch_unmap_area(struct mm_struct *mm, unsigned long addr)
 {
 }
 
diff --git a/mm/oom_kill.c b/mm/oom_kill.c
index 4bbb1cb..59666d9 100644
--- a/mm/oom_kill.c
+++ b/mm/oom_kill.c
@@ -258,6 +258,10 @@
 	struct mm_struct *mm = NULL;
 	task_t * p;
 
+	printk("oom-killer: gfp_mask=0x%x\n", gfp_mask);
+	/* print memory stats */
+	show_mem();
+
 	read_lock(&tasklist_lock);
 retry:
 	p = select_bad_process();
@@ -268,12 +272,9 @@
 	/* Found nothing?!?! Either we hang forever, or we panic. */
 	if (!p) {
 		read_unlock(&tasklist_lock);
-		show_free_areas();
 		panic("Out of memory and no killable processes...\n");
 	}
 
-	printk("oom-killer: gfp_mask=0x%x\n", gfp_mask);
-	show_free_areas();
 	mm = oom_kill_process(p);
 	if (!mm)
 		goto retry;
diff --git a/mm/page_alloc.c b/mm/page_alloc.c
index b1061b1..2069207 100644
--- a/mm/page_alloc.c
+++ b/mm/page_alloc.c
@@ -105,11 +105,13 @@
 	printk(KERN_EMERG "Backtrace:\n");
 	dump_stack();
 	printk(KERN_EMERG "Trying to fix it up, but a reboot is needed\n");
-	page->flags &= ~(1 << PG_private	|
+	page->flags &= ~(1 << PG_lru	|
+			1 << PG_private |
 			1 << PG_locked	|
-			1 << PG_lru	|
 			1 << PG_active	|
 			1 << PG_dirty	|
+			1 << PG_reclaim |
+			1 << PG_slab    |
 			1 << PG_swapcache |
 			1 << PG_writeback);
 	set_page_count(page, 0);
@@ -440,14 +442,17 @@
  */
 static void prep_new_page(struct page *page, int order)
 {
-	if (page->mapping || page_mapcount(page) ||
-	    (page->flags & (
+	if (	page_mapcount(page) ||
+		page->mapping != NULL ||
+		page_count(page) != 0 ||
+		(page->flags & (
+			1 << PG_lru	|
 			1 << PG_private	|
 			1 << PG_locked	|
-			1 << PG_lru	|
 			1 << PG_active	|
 			1 << PG_dirty	|
 			1 << PG_reclaim	|
+			1 << PG_slab    |
 			1 << PG_swapcache |
 			1 << PG_writeback )))
 		bad_page(__FUNCTION__, page);
@@ -511,6 +516,36 @@
 	return allocated;
 }
 
+#ifdef CONFIG_NUMA
+/* Called from the slab reaper to drain remote pagesets */
+void drain_remote_pages(void)
+{
+	struct zone *zone;
+	int i;
+	unsigned long flags;
+
+	local_irq_save(flags);
+	for_each_zone(zone) {
+		struct per_cpu_pageset *pset;
+
+		/* Do not drain local pagesets */
+		if (zone->zone_pgdat->node_id == numa_node_id())
+			continue;
+
+		pset = zone->pageset[smp_processor_id()];
+		for (i = 0; i < ARRAY_SIZE(pset->pcp); i++) {
+			struct per_cpu_pages *pcp;
+
+			pcp = &pset->pcp[i];
+			if (pcp->count)
+				pcp->count -= free_pages_bulk(zone, pcp->count,
+						&pcp->list, 0);
+		}
+	}
+	local_irq_restore(flags);
+}
+#endif
+
 #if defined(CONFIG_PM) || defined(CONFIG_HOTPLUG_CPU)
 static void __drain_pages(unsigned int cpu)
 {
@@ -520,7 +555,7 @@
 	for_each_zone(zone) {
 		struct per_cpu_pageset *pset;
 
-		pset = &zone->pageset[cpu];
+		pset = zone_pcp(zone, cpu);
 		for (i = 0; i < ARRAY_SIZE(pset->pcp); i++) {
 			struct per_cpu_pages *pcp;
 
@@ -583,12 +618,12 @@
 
 	local_irq_save(flags);
 	cpu = smp_processor_id();
-	p = &z->pageset[cpu];
+	p = zone_pcp(z,cpu);
 	if (pg == orig) {
-		z->pageset[cpu].numa_hit++;
+		p->numa_hit++;
 	} else {
 		p->numa_miss++;
-		zonelist->zones[0]->pageset[cpu].numa_foreign++;
+		zone_pcp(zonelist->zones[0], cpu)->numa_foreign++;
 	}
 	if (pg == NODE_DATA(numa_node_id()))
 		p->local_node++;
@@ -615,12 +650,12 @@
 	if (PageAnon(page))
 		page->mapping = NULL;
 	free_pages_check(__FUNCTION__, page);
-	pcp = &zone->pageset[get_cpu()].pcp[cold];
+	pcp = &zone_pcp(zone, get_cpu())->pcp[cold];
 	local_irq_save(flags);
-	if (pcp->count >= pcp->high)
-		pcp->count -= free_pages_bulk(zone, pcp->batch, &pcp->list, 0);
 	list_add(&page->lru, &pcp->list);
 	pcp->count++;
+	if (pcp->count >= pcp->high)
+		pcp->count -= free_pages_bulk(zone, pcp->batch, &pcp->list, 0);
 	local_irq_restore(flags);
 	put_cpu();
 }
@@ -659,7 +694,7 @@
 	if (order == 0) {
 		struct per_cpu_pages *pcp;
 
-		pcp = &zone->pageset[get_cpu()].pcp[cold];
+		pcp = &zone_pcp(zone, get_cpu())->pcp[cold];
 		local_irq_save(flags);
 		if (pcp->count <= pcp->low)
 			pcp->count += rmqueue_bulk(zone, 0,
@@ -724,6 +759,16 @@
 	return 1;
 }
 
+static inline int
+should_reclaim_zone(struct zone *z, unsigned int gfp_mask)
+{
+	if (!z->reclaim_pages)
+		return 0;
+	if (gfp_mask & __GFP_NORECLAIM)
+		return 0;
+	return 1;
+}
+
 /*
  * This is the 'heart' of the zoned buddy allocator.
  */
@@ -760,17 +805,32 @@
 
 	classzone_idx = zone_idx(zones[0]);
 
- restart:
+restart:
 	/* Go through the zonelist once, looking for a zone with enough free */
 	for (i = 0; (z = zones[i]) != NULL; i++) {
-
-		if (!zone_watermark_ok(z, order, z->pages_low,
-				       classzone_idx, 0, 0))
-			continue;
+		int do_reclaim = should_reclaim_zone(z, gfp_mask);
 
 		if (!cpuset_zone_allowed(z))
 			continue;
 
+		/*
+		 * If the zone is to attempt early page reclaim then this loop
+		 * will try to reclaim pages and check the watermark a second
+		 * time before giving up and falling back to the next zone.
+		 */
+zone_reclaim_retry:
+		if (!zone_watermark_ok(z, order, z->pages_low,
+				       classzone_idx, 0, 0)) {
+			if (!do_reclaim)
+				continue;
+			else {
+				zone_reclaim(z, gfp_mask, order);
+				/* Only try reclaim once */
+				do_reclaim = 0;
+				goto zone_reclaim_retry;
+			}
+		}
+
 		page = buffered_rmqueue(z, order, gfp_mask);
 		if (page)
 			goto got_pg;
@@ -829,7 +889,7 @@
 	reclaim_state.reclaimed_slab = 0;
 	p->reclaim_state = &reclaim_state;
 
-	did_some_progress = try_to_free_pages(zones, gfp_mask, order);
+	did_some_progress = try_to_free_pages(zones, gfp_mask);
 
 	p->reclaim_state = NULL;
 	p->flags &= ~PF_MEMALLOC;
@@ -905,6 +965,7 @@
 			" order:%d, mode:0x%x\n",
 			p->comm, order, gfp_mask);
 		dump_stack();
+		show_mem();
 	}
 	return NULL;
 got_pg:
@@ -1114,7 +1175,7 @@
 	__get_page_state(ret, sizeof(*ret) / sizeof(unsigned long));
 }
 
-unsigned long __read_page_state(unsigned offset)
+unsigned long __read_page_state(unsigned long offset)
 {
 	unsigned long ret = 0;
 	int cpu;
@@ -1128,7 +1189,7 @@
 	return ret;
 }
 
-void __mod_page_state(unsigned offset, unsigned long delta)
+void __mod_page_state(unsigned long offset, unsigned long delta)
 {
 	unsigned long flags;
 	void* ptr;
@@ -1237,22 +1298,23 @@
 			if (!cpu_possible(cpu))
 				continue;
 
-			pageset = zone->pageset + cpu;
+			pageset = zone_pcp(zone, cpu);
 
 			for (temperature = 0; temperature < 2; temperature++)
-				printk("cpu %d %s: low %d, high %d, batch %d\n",
+				printk("cpu %d %s: low %d, high %d, batch %d used:%d\n",
 					cpu,
 					temperature ? "cold" : "hot",
 					pageset->pcp[temperature].low,
 					pageset->pcp[temperature].high,
-					pageset->pcp[temperature].batch);
+					pageset->pcp[temperature].batch,
+					pageset->pcp[temperature].count);
 		}
 	}
 
 	get_page_state(&ps);
 	get_zone_counts(&active, &inactive, &free);
 
-	printk("\nFree pages: %11ukB (%ukB HighMem)\n",
+	printk("Free pages: %11ukB (%ukB HighMem)\n",
 		K(nr_free_pages()),
 		K(nr_free_highpages()));
 
@@ -1620,6 +1682,155 @@
 	memmap_init_zone((size), (nid), (zone), (start_pfn))
 #endif
 
+static int __devinit zone_batchsize(struct zone *zone)
+{
+	int batch;
+
+	/*
+	 * The per-cpu-pages pools are set to around 1000th of the
+	 * size of the zone.  But no more than 1/4 of a meg - there's
+	 * no point in going beyond the size of L2 cache.
+	 *
+	 * OK, so we don't know how big the cache is.  So guess.
+	 */
+	batch = zone->present_pages / 1024;
+	if (batch * PAGE_SIZE > 256 * 1024)
+		batch = (256 * 1024) / PAGE_SIZE;
+	batch /= 4;		/* We effectively *= 4 below */
+	if (batch < 1)
+		batch = 1;
+
+	/*
+	 * Clamp the batch to a 2^n - 1 value. Having a power
+	 * of 2 value was found to be more likely to have
+	 * suboptimal cache aliasing properties in some cases.
+	 *
+	 * For example if 2 tasks are alternately allocating
+	 * batches of pages, one task can end up with a lot
+	 * of pages of one half of the possible page colors
+	 * and the other with pages of the other colors.
+	 */
+	batch = (1 << fls(batch + batch/2)) - 1;
+	return batch;
+}
+
+inline void setup_pageset(struct per_cpu_pageset *p, unsigned long batch)
+{
+	struct per_cpu_pages *pcp;
+
+	pcp = &p->pcp[0];		/* hot */
+	pcp->count = 0;
+	pcp->low = 2 * batch;
+	pcp->high = 6 * batch;
+	pcp->batch = max(1UL, 1 * batch);
+	INIT_LIST_HEAD(&pcp->list);
+
+	pcp = &p->pcp[1];		/* cold*/
+	pcp->count = 0;
+	pcp->low = 0;
+	pcp->high = 2 * batch;
+	pcp->batch = max(1UL, 1 * batch);
+	INIT_LIST_HEAD(&pcp->list);
+}
+
+#ifdef CONFIG_NUMA
+/*
+ * Boot pageset table. One per cpu which is going to be used for all
+ * zones and all nodes. The parameters will be set in such a way
+ * that an item put on a list will immediately be handed over to
+ * the buddy list. This is safe since pageset manipulation is done
+ * with interrupts disabled.
+ *
+ * Some NUMA counter updates may also be caught by the boot pagesets.
+ * These will be discarded when bootup is complete.
+ */
+static struct per_cpu_pageset
+	boot_pageset[NR_CPUS] __initdata;
+
+/*
+ * Dynamically allocate memory for the
+ * per cpu pageset array in struct zone.
+ */
+static int __devinit process_zones(int cpu)
+{
+	struct zone *zone, *dzone;
+
+	for_each_zone(zone) {
+
+		zone->pageset[cpu] = kmalloc_node(sizeof(struct per_cpu_pageset),
+					 GFP_KERNEL, cpu_to_node(cpu));
+		if (!zone->pageset[cpu])
+			goto bad;
+
+		setup_pageset(zone->pageset[cpu], zone_batchsize(zone));
+	}
+
+	return 0;
+bad:
+	for_each_zone(dzone) {
+		if (dzone == zone)
+			break;
+		kfree(dzone->pageset[cpu]);
+		dzone->pageset[cpu] = NULL;
+	}
+	return -ENOMEM;
+}
+
+static inline void free_zone_pagesets(int cpu)
+{
+#ifdef CONFIG_NUMA
+	struct zone *zone;
+
+	for_each_zone(zone) {
+		struct per_cpu_pageset *pset = zone_pcp(zone, cpu);
+
+		zone_pcp(zone, cpu) = NULL;
+		kfree(pset);
+	}
+#endif
+}
+
+static int __devinit pageset_cpuup_callback(struct notifier_block *nfb,
+		unsigned long action,
+		void *hcpu)
+{
+	int cpu = (long)hcpu;
+	int ret = NOTIFY_OK;
+
+	switch (action) {
+		case CPU_UP_PREPARE:
+			if (process_zones(cpu))
+				ret = NOTIFY_BAD;
+			break;
+#ifdef CONFIG_HOTPLUG_CPU
+		case CPU_DEAD:
+			free_zone_pagesets(cpu);
+			break;
+#endif
+		default:
+			break;
+	}
+	return ret;
+}
+
+static struct notifier_block pageset_notifier =
+	{ &pageset_cpuup_callback, NULL, 0 };
+
+void __init setup_per_cpu_pageset()
+{
+	int err;
+
+	/* Initialize per_cpu_pageset for cpu 0.
+	 * A cpuup callback will do this for every cpu
+	 * as it comes online
+	 */
+	err = process_zones(smp_processor_id());
+	BUG_ON(err);
+	register_cpu_notifier(&pageset_notifier);
+}
+
+#endif
+
 /*
  * Set up the zone data structures:
  *   - mark all pages reserved
@@ -1662,48 +1873,16 @@
 
 		zone->temp_priority = zone->prev_priority = DEF_PRIORITY;
 
-		/*
-		 * The per-cpu-pages pools are set to around 1000th of the
-		 * size of the zone.  But no more than 1/4 of a meg - there's
-		 * no point in going beyond the size of L2 cache.
-		 *
-		 * OK, so we don't know how big the cache is.  So guess.
-		 */
-		batch = zone->present_pages / 1024;
-		if (batch * PAGE_SIZE > 256 * 1024)
-			batch = (256 * 1024) / PAGE_SIZE;
-		batch /= 4;		/* We effectively *= 4 below */
-		if (batch < 1)
-			batch = 1;
-
-		/*
-		 * Clamp the batch to a 2^n - 1 value. Having a power
-		 * of 2 value was found to be more likely to have
-		 * suboptimal cache aliasing properties in some cases.
-		 *
-		 * For example if 2 tasks are alternately allocating
-		 * batches of pages, one task can end up with a lot
-		 * of pages of one half of the possible page colors
-		 * and the other with pages of the other colors.
-		 */
-		batch = (1 << fls(batch + batch/2)) - 1;
+		batch = zone_batchsize(zone);
 
 		for (cpu = 0; cpu < NR_CPUS; cpu++) {
-			struct per_cpu_pages *pcp;
-
-			pcp = &zone->pageset[cpu].pcp[0];	/* hot */
-			pcp->count = 0;
-			pcp->low = 2 * batch;
-			pcp->high = 6 * batch;
-			pcp->batch = 1 * batch;
-			INIT_LIST_HEAD(&pcp->list);
-
-			pcp = &zone->pageset[cpu].pcp[1];	/* cold */
-			pcp->count = 0;
-			pcp->low = 0;
-			pcp->high = 2 * batch;
-			pcp->batch = 1 * batch;
-			INIT_LIST_HEAD(&pcp->list);
+#ifdef CONFIG_NUMA
+			/* Early boot. Slab allocator not functional yet */
+			zone->pageset[cpu] = &boot_pageset[cpu];
+			setup_pageset(&boot_pageset[cpu],0);
+#else
+			setup_pageset(zone_pcp(zone,cpu), batch);
+#endif
 		}
 		printk(KERN_DEBUG "  %s zone: %lu pages, LIFO batch:%lu\n",
 				zone_names[j], realsize, batch);
@@ -1713,6 +1892,7 @@
 		zone->nr_scan_inactive = 0;
 		zone->nr_active = 0;
 		zone->nr_inactive = 0;
+		atomic_set(&zone->reclaim_in_progress, -1);
 		if (!size)
 			continue;
 
@@ -1853,6 +2033,115 @@
 	.show	= frag_show,
 };
 
+/*
+ * Output information about zones in @pgdat.
+ */
+static int zoneinfo_show(struct seq_file *m, void *arg)
+{
+	pg_data_t *pgdat = arg;
+	struct zone *zone;
+	struct zone *node_zones = pgdat->node_zones;
+	unsigned long flags;
+
+	for (zone = node_zones; zone - node_zones < MAX_NR_ZONES; zone++) {
+		int i;
+
+		if (!zone->present_pages)
+			continue;
+
+		spin_lock_irqsave(&zone->lock, flags);
+		seq_printf(m, "Node %d, zone %8s", pgdat->node_id, zone->name);
+		seq_printf(m,
+			   "\n  pages free     %lu"
+			   "\n        min      %lu"
+			   "\n        low      %lu"
+			   "\n        high     %lu"
+			   "\n        active   %lu"
+			   "\n        inactive %lu"
+			   "\n        scanned  %lu (a: %lu i: %lu)"
+			   "\n        spanned  %lu"
+			   "\n        present  %lu",
+			   zone->free_pages,
+			   zone->pages_min,
+			   zone->pages_low,
+			   zone->pages_high,
+			   zone->nr_active,
+			   zone->nr_inactive,
+			   zone->pages_scanned,
+			   zone->nr_scan_active, zone->nr_scan_inactive,
+			   zone->spanned_pages,
+			   zone->present_pages);
+		seq_printf(m,
+			   "\n        protection: (%lu",
+			   zone->lowmem_reserve[0]);
+		for (i = 1; i < ARRAY_SIZE(zone->lowmem_reserve); i++)
+			seq_printf(m, ", %lu", zone->lowmem_reserve[i]);
+		seq_printf(m,
+			   ")"
+			   "\n  pagesets");
+		for (i = 0; i < ARRAY_SIZE(zone->pageset); i++) {
+			struct per_cpu_pageset *pageset;
+			int j;
+
+			pageset = zone_pcp(zone, i);
+			for (j = 0; j < ARRAY_SIZE(pageset->pcp); j++) {
+				if (pageset->pcp[j].count)
+					break;
+			}
+			if (j == ARRAY_SIZE(pageset->pcp))
+				continue;
+			for (j = 0; j < ARRAY_SIZE(pageset->pcp); j++) {
+				seq_printf(m,
+					   "\n    cpu: %i pcp: %i"
+					   "\n              count: %i"
+					   "\n              low:   %i"
+					   "\n              high:  %i"
+					   "\n              batch: %i",
+					   i, j,
+					   pageset->pcp[j].count,
+					   pageset->pcp[j].low,
+					   pageset->pcp[j].high,
+					   pageset->pcp[j].batch);
+			}
+#ifdef CONFIG_NUMA
+			seq_printf(m,
+				   "\n            numa_hit:       %lu"
+				   "\n            numa_miss:      %lu"
+				   "\n            numa_foreign:   %lu"
+				   "\n            interleave_hit: %lu"
+				   "\n            local_node:     %lu"
+				   "\n            other_node:     %lu",
+				   pageset->numa_hit,
+				   pageset->numa_miss,
+				   pageset->numa_foreign,
+				   pageset->interleave_hit,
+				   pageset->local_node,
+				   pageset->other_node);
+#endif
+		}
+		seq_printf(m,
+			   "\n  all_unreclaimable: %u"
+			   "\n  prev_priority:     %i"
+			   "\n  temp_priority:     %i"
+			   "\n  start_pfn:         %lu",
+			   zone->all_unreclaimable,
+			   zone->prev_priority,
+			   zone->temp_priority,
+			   zone->zone_start_pfn);
+		spin_unlock_irqrestore(&zone->lock, flags);
+		seq_putc(m, '\n');
+	}
+	return 0;
+}
+
+struct seq_operations zoneinfo_op = {
+	.start	= frag_start, /* iterate over all zones. The same as in
+			       * fragmentation. */
+	.next	= frag_next,
+	.stop	= frag_stop,
+	.show	= zoneinfo_show,
+};
+
 static char *vmstat_text[] = {
 	"nr_dirty",
 	"nr_writeback",
@@ -2058,10 +2347,10 @@
 				min_pages = 128;
 			zone->pages_min = min_pages;
 		} else {
-			/* if it's a lowmem zone, reserve a number of pages 
+			/* if it's a lowmem zone, reserve a number of pages
 			 * proportionate to the zone's size.
 			 */
-			zone->pages_min = (pages_min * zone->present_pages) / 
+			zone->pages_min = (pages_min * zone->present_pages) /
 			                   lowmem_pages;
 		}
 
diff --git a/mm/rmap.c b/mm/rmap.c
index 9827409..89770bd 100644
--- a/mm/rmap.c
+++ b/mm/rmap.c
@@ -539,27 +539,6 @@
 		goto out_unmap;
 	}
 
-	/*
-	 * Don't pull an anonymous page out from under get_user_pages.
-	 * GUP carefully breaks COW and raises page count (while holding
-	 * page_table_lock, as we have here) to make sure that the page
-	 * cannot be freed.  If we unmap that page here, a user write
-	 * access to the virtual address will bring back the page, but
-	 * its raised count will (ironically) be taken to mean it's not
-	 * an exclusive swap page, do_wp_page will replace it by a copy
-	 * page, and the user never get to see the data GUP was holding
-	 * the original page for.
-	 *
-	 * This test is also useful for when swapoff (unuse_process) has
-	 * to drop page lock: its reference to the page stops existing
-	 * ptes from being unmapped, so swapoff can make progress.
-	 */
-	if (PageSwapCache(page) &&
-	    page_count(page) != page_mapcount(page) + 2) {
-		ret = SWAP_FAIL;
-		goto out_unmap;
-	}
-
 	/* Nuke the page table entry. */
 	flush_cache_page(vma, address, page_to_pfn(page));
 	pteval = ptep_clear_flush(vma, address, pte);
diff --git a/mm/shmem.c b/mm/shmem.c
index 61574b8..e64fa72 100644
--- a/mm/shmem.c
+++ b/mm/shmem.c
@@ -6,8 +6,8 @@
  *		 2000-2001 Christoph Rohland
  *		 2000-2001 SAP AG
  *		 2002 Red Hat Inc.
- * Copyright (C) 2002-2004 Hugh Dickins.
- * Copyright (C) 2002-2004 VERITAS Software Corporation.
+ * Copyright (C) 2002-2005 Hugh Dickins.
+ * Copyright (C) 2002-2005 VERITAS Software Corporation.
  * Copyright (C) 2004 Andi Kleen, SuSE Labs
  *
  * Extended attribute support for tmpfs:
@@ -194,7 +194,7 @@
 static void shmem_free_blocks(struct inode *inode, long pages)
 {
 	struct shmem_sb_info *sbinfo = SHMEM_SB(inode->i_sb);
-	if (sbinfo) {
+	if (sbinfo->max_blocks) {
 		spin_lock(&sbinfo->stat_lock);
 		sbinfo->free_blocks += pages;
 		inode->i_blocks -= pages*BLOCKS_PER_PAGE;
@@ -357,7 +357,7 @@
 		 * page (and perhaps indirect index pages) yet to allocate:
 		 * a waste to allocate index if we cannot allocate data.
 		 */
-		if (sbinfo) {
+		if (sbinfo->max_blocks) {
 			spin_lock(&sbinfo->stat_lock);
 			if (sbinfo->free_blocks <= 1) {
 				spin_unlock(&sbinfo->stat_lock);
@@ -677,8 +677,8 @@
 			spin_unlock(&shmem_swaplist_lock);
 		}
 	}
-	if (sbinfo) {
-		BUG_ON(inode->i_blocks);
+	BUG_ON(inode->i_blocks);
+	if (sbinfo->max_inodes) {
 		spin_lock(&sbinfo->stat_lock);
 		sbinfo->free_inodes++;
 		spin_unlock(&sbinfo->stat_lock);
@@ -1080,7 +1080,7 @@
 	} else {
 		shmem_swp_unmap(entry);
 		sbinfo = SHMEM_SB(inode->i_sb);
-		if (sbinfo) {
+		if (sbinfo->max_blocks) {
 			spin_lock(&sbinfo->stat_lock);
 			if (sbinfo->free_blocks == 0 ||
 			    shmem_acct_block(info->flags)) {
@@ -1269,7 +1269,7 @@
 	struct shmem_inode_info *info;
 	struct shmem_sb_info *sbinfo = SHMEM_SB(sb);
 
-	if (sbinfo) {
+	if (sbinfo->max_inodes) {
 		spin_lock(&sbinfo->stat_lock);
 		if (!sbinfo->free_inodes) {
 			spin_unlock(&sbinfo->stat_lock);
@@ -1319,7 +1319,7 @@
 			mpol_shared_policy_init(&info->policy);
 			break;
 		}
-	} else if (sbinfo) {
+	} else if (sbinfo->max_inodes) {
 		spin_lock(&sbinfo->stat_lock);
 		sbinfo->free_inodes++;
 		spin_unlock(&sbinfo->stat_lock);
@@ -1328,31 +1328,6 @@
 }
 
 #ifdef CONFIG_TMPFS
-
-static int shmem_set_size(struct shmem_sb_info *sbinfo,
-			  unsigned long max_blocks, unsigned long max_inodes)
-{
-	int error;
-	unsigned long blocks, inodes;
-
-	spin_lock(&sbinfo->stat_lock);
-	blocks = sbinfo->max_blocks - sbinfo->free_blocks;
-	inodes = sbinfo->max_inodes - sbinfo->free_inodes;
-	error = -EINVAL;
-	if (max_blocks < blocks)
-		goto out;
-	if (max_inodes < inodes)
-		goto out;
-	error = 0;
-	sbinfo->max_blocks  = max_blocks;
-	sbinfo->free_blocks = max_blocks - blocks;
-	sbinfo->max_inodes  = max_inodes;
-	sbinfo->free_inodes = max_inodes - inodes;
-out:
-	spin_unlock(&sbinfo->stat_lock);
-	return error;
-}
-
 static struct inode_operations shmem_symlink_inode_operations;
 static struct inode_operations shmem_symlink_inline_operations;
 
@@ -1607,15 +1582,17 @@
 	buf->f_type = TMPFS_MAGIC;
 	buf->f_bsize = PAGE_CACHE_SIZE;
 	buf->f_namelen = NAME_MAX;
-	if (sbinfo) {
-		spin_lock(&sbinfo->stat_lock);
+	spin_lock(&sbinfo->stat_lock);
+	if (sbinfo->max_blocks) {
 		buf->f_blocks = sbinfo->max_blocks;
 		buf->f_bavail = buf->f_bfree = sbinfo->free_blocks;
+	}
+	if (sbinfo->max_inodes) {
 		buf->f_files = sbinfo->max_inodes;
 		buf->f_ffree = sbinfo->free_inodes;
-		spin_unlock(&sbinfo->stat_lock);
 	}
 	/* else leave those fields 0 like simple_statfs */
+	spin_unlock(&sbinfo->stat_lock);
 	return 0;
 }
 
@@ -1672,7 +1649,7 @@
 	 * but each new link needs a new dentry, pinning lowmem, and
 	 * tmpfs dentries cannot be pruned until they are unlinked.
 	 */
-	if (sbinfo) {
+	if (sbinfo->max_inodes) {
 		spin_lock(&sbinfo->stat_lock);
 		if (!sbinfo->free_inodes) {
 			spin_unlock(&sbinfo->stat_lock);
@@ -1697,7 +1674,7 @@
 
 	if (inode->i_nlink > 1 && !S_ISDIR(inode->i_mode)) {
 		struct shmem_sb_info *sbinfo = SHMEM_SB(inode->i_sb);
-		if (sbinfo) {
+		if (sbinfo->max_inodes) {
 			spin_lock(&sbinfo->stat_lock);
 			sbinfo->free_inodes++;
 			spin_unlock(&sbinfo->stat_lock);
@@ -1921,22 +1898,42 @@
 static int shmem_remount_fs(struct super_block *sb, int *flags, char *data)
 {
 	struct shmem_sb_info *sbinfo = SHMEM_SB(sb);
-	unsigned long max_blocks = 0;
-	unsigned long max_inodes = 0;
+	unsigned long max_blocks = sbinfo->max_blocks;
+	unsigned long max_inodes = sbinfo->max_inodes;
+	unsigned long blocks;
+	unsigned long inodes;
+	int error = -EINVAL;
 
-	if (sbinfo) {
-		max_blocks = sbinfo->max_blocks;
-		max_inodes = sbinfo->max_inodes;
-	}
-	if (shmem_parse_options(data, NULL, NULL, NULL, &max_blocks, &max_inodes))
-		return -EINVAL;
-	/* Keep it simple: disallow limited <-> unlimited remount */
-	if ((max_blocks || max_inodes) == !sbinfo)
-		return -EINVAL;
-	/* But allow the pointless unlimited -> unlimited remount */
-	if (!sbinfo)
-		return 0;
-	return shmem_set_size(sbinfo, max_blocks, max_inodes);
+	if (shmem_parse_options(data, NULL, NULL, NULL,
+				&max_blocks, &max_inodes))
+		return error;
+
+	spin_lock(&sbinfo->stat_lock);
+	blocks = sbinfo->max_blocks - sbinfo->free_blocks;
+	inodes = sbinfo->max_inodes - sbinfo->free_inodes;
+	if (max_blocks < blocks)
+		goto out;
+	if (max_inodes < inodes)
+		goto out;
+	/*
+	 * Those tests also disallow limited->unlimited while any are in
+	 * use, so i_blocks will always be zero when max_blocks is zero;
+	 * but we must separately disallow unlimited->limited, because
+	 * in that case we have no record of how much is already in use.
+	 */
+	if (max_blocks && !sbinfo->max_blocks)
+		goto out;
+	if (max_inodes && !sbinfo->max_inodes)
+		goto out;
+
+	error = 0;
+	sbinfo->max_blocks  = max_blocks;
+	sbinfo->free_blocks = max_blocks - blocks;
+	sbinfo->max_inodes  = max_inodes;
+	sbinfo->free_inodes = max_inodes - inodes;
+out:
+	spin_unlock(&sbinfo->stat_lock);
+	return error;
 }
 #endif
 
@@ -1961,11 +1958,11 @@
 	uid_t uid = current->fsuid;
 	gid_t gid = current->fsgid;
 	int err = -ENOMEM;
-
-#ifdef CONFIG_TMPFS
+	struct shmem_sb_info *sbinfo;
 	unsigned long blocks = 0;
 	unsigned long inodes = 0;
 
+#ifdef CONFIG_TMPFS
 	/*
 	 * Per default we only allow half of the physical ram per
 	 * tmpfs instance, limiting inodes to one per page of lowmem;
@@ -1976,34 +1973,34 @@
 		inodes = totalram_pages - totalhigh_pages;
 		if (inodes > blocks)
 			inodes = blocks;
-
-		if (shmem_parse_options(data, &mode,
-					&uid, &gid, &blocks, &inodes))
+		if (shmem_parse_options(data, &mode, &uid, &gid,
+					&blocks, &inodes))
 			return -EINVAL;
 	}
-
-	if (blocks || inodes) {
-		struct shmem_sb_info *sbinfo;
-		sbinfo = kmalloc(sizeof(struct shmem_sb_info), GFP_KERNEL);
-		if (!sbinfo)
-			return -ENOMEM;
-		sb->s_fs_info = sbinfo;
-		spin_lock_init(&sbinfo->stat_lock);
-		sbinfo->max_blocks = blocks;
-		sbinfo->free_blocks = blocks;
-		sbinfo->max_inodes = inodes;
-		sbinfo->free_inodes = inodes;
-	}
-	sb->s_xattr = shmem_xattr_handlers;
 #else
 	sb->s_flags |= MS_NOUSER;
 #endif
 
+	/* Round up to L1_CACHE_BYTES to resist false sharing */
+	sbinfo = kmalloc(max((int)sizeof(struct shmem_sb_info),
+				L1_CACHE_BYTES), GFP_KERNEL);
+	if (!sbinfo)
+		return -ENOMEM;
+
+	spin_lock_init(&sbinfo->stat_lock);
+	sbinfo->max_blocks = blocks;
+	sbinfo->free_blocks = blocks;
+	sbinfo->max_inodes = inodes;
+	sbinfo->free_inodes = inodes;
+
+	sb->s_fs_info = sbinfo;
 	sb->s_maxbytes = SHMEM_MAX_BYTES;
 	sb->s_blocksize = PAGE_CACHE_SIZE;
 	sb->s_blocksize_bits = PAGE_CACHE_SHIFT;
 	sb->s_magic = TMPFS_MAGIC;
 	sb->s_op = &shmem_ops;
+	sb->s_xattr = shmem_xattr_handlers;
+
 	inode = shmem_get_inode(sb, S_IFDIR | mode, 0);
 	if (!inode)
 		goto failed;
diff --git a/mm/slab.c b/mm/slab.c
index c78d343..93cbbbb 100644
--- a/mm/slab.c
+++ b/mm/slab.c
@@ -2851,6 +2851,7 @@
 	}
 	check_irq_on();
 	up(&cache_chain_sem);
+	drain_remote_pages();
 	/* Setup the next iteration */
 	schedule_delayed_work(&__get_cpu_var(reap_work), REAPTIMEOUT_CPUC + smp_processor_id());
 }
diff --git a/mm/swapfile.c b/mm/swapfile.c
index da48405..60cd24a 100644
--- a/mm/swapfile.c
+++ b/mm/swapfile.c
@@ -276,61 +276,37 @@
 }
 
 /*
- * Check if we're the only user of a swap page,
- * when the page is locked.
+ * How many references to page are currently swapped out?
  */
-static int exclusive_swap_page(struct page *page)
+static inline int page_swapcount(struct page *page)
 {
-	int retval = 0;
-	struct swap_info_struct * p;
+	int count = 0;
+	struct swap_info_struct *p;
 	swp_entry_t entry;
 
 	entry.val = page->private;
 	p = swap_info_get(entry);
 	if (p) {
-		/* Is the only swap cache user the cache itself? */
-		if (p->swap_map[swp_offset(entry)] == 1) {
-			/* Recheck the page count with the swapcache lock held.. */
-			write_lock_irq(&swapper_space.tree_lock);
-			if (page_count(page) == 2)
-				retval = 1;
-			write_unlock_irq(&swapper_space.tree_lock);
-		}
+		/* Subtract the 1 for the swap cache itself */
+		count = p->swap_map[swp_offset(entry)] - 1;
 		swap_info_put(p);
 	}
-	return retval;
+	return count;
 }
 
 /*
  * We can use this swap cache entry directly
  * if there are no other references to it.
- *
- * Here "exclusive_swap_page()" does the real
- * work, but we opportunistically check whether
- * we need to get all the locks first..
  */
 int can_share_swap_page(struct page *page)
 {
-	int retval = 0;
+	int count;
 
-	if (!PageLocked(page))
-		BUG();
-	switch (page_count(page)) {
-	case 3:
-		if (!PagePrivate(page))
-			break;
-		/* Fallthrough */
-	case 2:
-		if (!PageSwapCache(page))
-			break;
-		retval = exclusive_swap_page(page);
-		break;
-	case 1:
-		if (PageReserved(page))
-			break;
-		retval = 1;
-	}
-	return retval;
+	BUG_ON(!PageLocked(page));
+	count = page_mapcount(page);
+	if (count <= 1 && PageSwapCache(page))
+		count += page_swapcount(page);
+	return count == 1;
 }
 
 /*
@@ -529,9 +505,10 @@
 
 	if (!down_read_trylock(&mm->mmap_sem)) {
 		/*
-		 * Our reference to the page stops try_to_unmap_one from
-		 * unmapping its ptes, so swapoff can make progress.
+		 * Activate page so shrink_cache is unlikely to unmap its
+		 * ptes while lock is dropped, so swapoff can make progress.
 		 */
+		activate_page(page);
 		unlock_page(page);
 		down_read(&mm->mmap_sem);
 		lock_page(page);
diff --git a/mm/vmscan.c b/mm/vmscan.c
index 269eded..4b8e62a 100644
--- a/mm/vmscan.c
+++ b/mm/vmscan.c
@@ -74,6 +74,9 @@
 
 	int may_writepage;
 
+	/* Can pages be swapped as part of reclaim? */
+	int may_swap;
+
 	/* This context's SWAP_CLUSTER_MAX. If freeing memory for
 	 * suspend, we effectively ignore SWAP_CLUSTER_MAX.
 	 * In this context, it doesn't matter that we scan the
@@ -180,17 +183,20 @@
  * `lru_pages' represents the number of on-LRU pages in all the zones which
  * are eligible for the caller's allocation attempt.  It is used for balancing
  * slab reclaim versus page reclaim.
+ *
+ * Returns the number of slab objects which we shrunk.
  */
 static int shrink_slab(unsigned long scanned, unsigned int gfp_mask,
 			unsigned long lru_pages)
 {
 	struct shrinker *shrinker;
+	int ret = 0;
 
 	if (scanned == 0)
 		scanned = SWAP_CLUSTER_MAX;
 
 	if (!down_read_trylock(&shrinker_rwsem))
-		return 0;
+		return 1;	/* Assume we'll be able to shrink next time */
 
 	list_for_each_entry(shrinker, &shrinker_list, list) {
 		unsigned long long delta;
@@ -209,10 +215,14 @@
 		while (total_scan >= SHRINK_BATCH) {
 			long this_scan = SHRINK_BATCH;
 			int shrink_ret;
+			int nr_before;
 
+			nr_before = (*shrinker->shrinker)(0, gfp_mask);
 			shrink_ret = (*shrinker->shrinker)(this_scan, gfp_mask);
 			if (shrink_ret == -1)
 				break;
+			if (shrink_ret < nr_before)
+				ret += nr_before - shrink_ret;
 			mod_page_state(slabs_scanned, this_scan);
 			total_scan -= this_scan;
 
@@ -222,7 +232,7 @@
 		shrinker->nr += total_scan;
 	}
 	up_read(&shrinker_rwsem);
-	return 0;
+	return ret;
 }
 
 /* Called without lock on whether page is mapped, so answer is unstable */
@@ -407,7 +417,7 @@
 		 * Anonymous process memory has backing store?
 		 * Try to allocate it some swap space here.
 		 */
-		if (PageAnon(page) && !PageSwapCache(page)) {
+		if (PageAnon(page) && !PageSwapCache(page) && sc->may_swap) {
 			if (!add_to_swap(page))
 				goto activate_locked;
 		}
@@ -890,7 +900,9 @@
 		if (zone->all_unreclaimable && sc->priority != DEF_PRIORITY)
 			continue;	/* Let kswapd poll it */
 
+		atomic_inc(&zone->reclaim_in_progress);
 		shrink_zone(zone, sc);
+		atomic_dec(&zone->reclaim_in_progress);
 	}
 }
  
@@ -907,8 +919,7 @@
  * holds filesystem locks which prevent writeout this might not work, and the
  * allocation attempt will fail.
  */
-int try_to_free_pages(struct zone **zones,
-		unsigned int gfp_mask, unsigned int order)
+int try_to_free_pages(struct zone **zones, unsigned int gfp_mask)
 {
 	int priority;
 	int ret = 0;
@@ -920,6 +931,7 @@
 
 	sc.gfp_mask = gfp_mask;
 	sc.may_writepage = 0;
+	sc.may_swap = 1;
 
 	inc_page_state(allocstall);
 
@@ -1020,6 +1032,7 @@
 	total_reclaimed = 0;
 	sc.gfp_mask = GFP_KERNEL;
 	sc.may_writepage = 0;
+	sc.may_swap = 1;
 	sc.nr_mapped = read_page_state(nr_mapped);
 
 	inc_page_state(pageoutrun);
@@ -1079,6 +1092,7 @@
 		 */
 		for (i = 0; i <= end_zone; i++) {
 			struct zone *zone = pgdat->node_zones + i;
+			int nr_slab;
 
 			if (zone->present_pages == 0)
 				continue;
@@ -1098,16 +1112,19 @@
 			sc.nr_reclaimed = 0;
 			sc.priority = priority;
 			sc.swap_cluster_max = nr_pages? nr_pages : SWAP_CLUSTER_MAX;
+			atomic_inc(&zone->reclaim_in_progress);
 			shrink_zone(zone, &sc);
+			atomic_dec(&zone->reclaim_in_progress);
 			reclaim_state->reclaimed_slab = 0;
-			shrink_slab(sc.nr_scanned, GFP_KERNEL, lru_pages);
+			nr_slab = shrink_slab(sc.nr_scanned, GFP_KERNEL,
+						lru_pages);
 			sc.nr_reclaimed += reclaim_state->reclaimed_slab;
 			total_reclaimed += sc.nr_reclaimed;
 			total_scanned += sc.nr_scanned;
 			if (zone->all_unreclaimable)
 				continue;
-			if (zone->pages_scanned >= (zone->nr_active +
-							zone->nr_inactive) * 4)
+			if (nr_slab == 0 && zone->pages_scanned >=
+				    (zone->nr_active + zone->nr_inactive) * 4)
 				zone->all_unreclaimable = 1;
 			/*
 			 * If we've done a decent amount of scanning and
@@ -1309,3 +1326,73 @@
 }
 
 module_init(kswapd_init)
+
+
+/*
+ * Try to free up some pages from this zone through reclaim.
+ */
+int zone_reclaim(struct zone *zone, unsigned int gfp_mask, unsigned int order)
+{
+	struct scan_control sc;
+	int nr_pages = 1 << order;
+	int total_reclaimed = 0;
+
+	/* The reclaim may sleep, so don't do it if sleep isn't allowed */
+	if (!(gfp_mask & __GFP_WAIT))
+		return 0;
+	if (zone->all_unreclaimable)
+		return 0;
+
+	sc.gfp_mask = gfp_mask;
+	sc.may_writepage = 0;
+	sc.may_swap = 0;
+	sc.nr_mapped = read_page_state(nr_mapped);
+	sc.nr_scanned = 0;
+	sc.nr_reclaimed = 0;
+	/* scan at the highest priority */
+	sc.priority = 0;
+
+	if (nr_pages > SWAP_CLUSTER_MAX)
+		sc.swap_cluster_max = nr_pages;
+	else
+		sc.swap_cluster_max = SWAP_CLUSTER_MAX;
+
+	/* Don't reclaim the zone if there are other reclaimers active */
+	if (!atomic_inc_and_test(&zone->reclaim_in_progress))
+		goto out;
+
+	shrink_zone(zone, &sc);
+	total_reclaimed = sc.nr_reclaimed;
+
+ out:
+	atomic_dec(&zone->reclaim_in_progress);
+	return total_reclaimed;
+}
+
+asmlinkage long sys_set_zone_reclaim(unsigned int node, unsigned int zone,
+				     unsigned int state)
+{
+	struct zone *z;
+	int i;
+
+	if (node >= MAX_NUMNODES || !node_online(node))
+		return -EINVAL;
+
+	/* This will break if we ever add more zones */
+	if (!(zone & (1<<ZONE_DMA|1<<ZONE_NORMAL|1<<ZONE_HIGHMEM)))
+		return -EINVAL;
+
+	for (i = 0; i < MAX_NR_ZONES; i++) {
+		if (!(zone & 1<<i))
+			continue;
+
+		z = &NODE_DATA(node)->node_zones[i];
+
+		if (state)
+			z->reclaim_pages = 1;
+		else
+			z->reclaim_pages = 0;
+	}
+
+	return 0;
+}
diff --git a/net/bridge/br_forward.c b/net/bridge/br_forward.c
index ef9f209..069253f 100644
--- a/net/bridge/br_forward.c
+++ b/net/bridge/br_forward.c
@@ -57,9 +57,6 @@
 static void __br_deliver(const struct net_bridge_port *to, struct sk_buff *skb)
 {
 	skb->dev = to->dev;
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug = 0;
-#endif
 	NF_HOOK(PF_BRIDGE, NF_BR_LOCAL_OUT, skb, NULL, skb->dev,
 			br_forward_finish);
 }
diff --git a/net/bridge/br_input.c b/net/bridge/br_input.c
index 8f5f2e7..9a45e62 100644
--- a/net/bridge/br_input.c
+++ b/net/bridge/br_input.c
@@ -23,11 +23,7 @@
 
 static int br_pass_frame_up_finish(struct sk_buff *skb)
 {
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug = 0;
-#endif
 	netif_receive_skb(skb);
-
 	return 0;
 }
 
diff --git a/net/bridge/br_netfilter.c b/net/bridge/br_netfilter.c
index be03d3a..03ae4ed 100644
--- a/net/bridge/br_netfilter.c
+++ b/net/bridge/br_netfilter.c
@@ -102,10 +102,6 @@
 {
 	struct nf_bridge_info *nf_bridge = skb->nf_bridge;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_BR_PRE_ROUTING);
-#endif
-
 	if (nf_bridge->mask & BRNF_PKT_TYPE) {
 		skb->pkt_type = PACKET_OTHERHOST;
 		nf_bridge->mask ^= BRNF_PKT_TYPE;
@@ -182,10 +178,6 @@
  * --Bart, 20021007 (updated) */
 static int br_nf_pre_routing_finish_bridge(struct sk_buff *skb)
 {
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug |= (1 << NF_BR_PRE_ROUTING) | (1 << NF_BR_FORWARD);
-#endif
-
 	if (skb->pkt_type == PACKET_OTHERHOST) {
 		skb->pkt_type = PACKET_HOST;
 		skb->nf_bridge->mask |= BRNF_PKT_TYPE;
@@ -207,10 +199,6 @@
 	struct iphdr *iph = skb->nh.iph;
 	struct nf_bridge_info *nf_bridge = skb->nf_bridge;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_BR_PRE_ROUTING);
-#endif
-
 	if (nf_bridge->mask & BRNF_PKT_TYPE) {
 		skb->pkt_type = PACKET_OTHERHOST;
 		nf_bridge->mask ^= BRNF_PKT_TYPE;
@@ -382,9 +370,6 @@
 	if (hdr->nexthdr == NEXTHDR_HOP && check_hbh_len(skb))
 			goto inhdr_error;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_IP6_PRE_ROUTING);
-#endif
 	if ((nf_bridge = nf_bridge_alloc(skb)) == NULL)
 		return NF_DROP;
 	setup_pre_routing(skb);
@@ -468,9 +453,6 @@
 			skb->ip_summed = CHECKSUM_NONE;
 	}
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_IP_PRE_ROUTING);
-#endif
 	if ((nf_bridge = nf_bridge_alloc(skb)) == NULL)
 		return NF_DROP;
 	setup_pre_routing(skb);
@@ -517,10 +499,6 @@
 	struct net_device *in;
 	struct vlan_ethhdr *hdr = vlan_eth_hdr(skb);
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_BR_FORWARD);
-#endif
-
 	if (skb->protocol != __constant_htons(ETH_P_ARP) && !IS_VLAN_ARP) {
 		in = nf_bridge->physindev;
 		if (nf_bridge->mask & BRNF_PKT_TYPE) {
@@ -566,9 +544,6 @@
 		(*pskb)->nh.raw += VLAN_HLEN;
 	}
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_BR_FORWARD);
-#endif
 	nf_bridge = skb->nf_bridge;
 	if (skb->pkt_type == PACKET_OTHERHOST) {
 		skb->pkt_type = PACKET_HOST;
@@ -605,10 +580,6 @@
 		(*pskb)->nh.raw += VLAN_HLEN;
 	}
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug ^= (1 << NF_BR_FORWARD);
-#endif
-
 	if (skb->nh.arph->ar_pln != 4) {
 		if (IS_VLAN_ARP) {
 			skb_push(*pskb, VLAN_HLEN);
@@ -627,9 +598,6 @@
 /* PF_BRIDGE/LOCAL_OUT ***********************************************/
 static int br_nf_local_out_finish(struct sk_buff *skb)
 {
-#ifdef CONFIG_NETFILTER_DEBUG
-	skb->nf_debug &= ~(1 << NF_BR_LOCAL_OUT);
-#endif
 	if (skb->protocol == __constant_htons(ETH_P_8021Q)) {
 		skb_push(skb, VLAN_HLEN);
 		skb->nh.raw -= VLAN_HLEN;
@@ -731,10 +699,6 @@
 			       realoutdev, br_nf_local_out_finish,
 			       NF_IP_PRI_BRIDGE_SABOTAGE_FORWARD + 1);
 	} else {
-#ifdef CONFIG_NETFILTER_DEBUG
-		skb->nf_debug ^= (1 << NF_IP_LOCAL_OUT);
-#endif
-
 		NF_HOOK_THRESH(pf, NF_IP_LOCAL_OUT, skb, realindev,
 			       realoutdev, br_nf_local_out_finish,
 			       NF_IP_PRI_BRIDGE_SABOTAGE_LOCAL_OUT + 1);
@@ -779,8 +743,6 @@
 		printk(KERN_CRIT "br_netfilter: skb->dst == NULL.");
 		goto print_error;
 	}
-
-	skb->nf_debug ^= (1 << NF_IP_POST_ROUTING);
 #endif
 
 	/* We assume any code from br_dev_queue_push_xmit onwards doesn't care
diff --git a/net/core/netfilter.c b/net/core/netfilter.c
index 22a8f12..076c156 100644
--- a/net/core/netfilter.c
+++ b/net/core/netfilter.c
@@ -141,136 +141,6 @@
 	up(&nf_sockopt_mutex);
 }
 
-#ifdef CONFIG_NETFILTER_DEBUG
-#include <net/ip.h>
-#include <net/tcp.h>
-#include <linux/netfilter_ipv4.h>
-
-static void debug_print_hooks_ip(unsigned int nf_debug)
-{
-	if (nf_debug & (1 << NF_IP_PRE_ROUTING)) {
-		printk("PRE_ROUTING ");
-		nf_debug ^= (1 << NF_IP_PRE_ROUTING);
-	}
-	if (nf_debug & (1 << NF_IP_LOCAL_IN)) {
-		printk("LOCAL_IN ");
-		nf_debug ^= (1 << NF_IP_LOCAL_IN);
-	}
-	if (nf_debug & (1 << NF_IP_FORWARD)) {
-		printk("FORWARD ");
-		nf_debug ^= (1 << NF_IP_FORWARD);
-	}
-	if (nf_debug & (1 << NF_IP_LOCAL_OUT)) {
-		printk("LOCAL_OUT ");
-		nf_debug ^= (1 << NF_IP_LOCAL_OUT);
-	}
-	if (nf_debug & (1 << NF_IP_POST_ROUTING)) {
-		printk("POST_ROUTING ");
-		nf_debug ^= (1 << NF_IP_POST_ROUTING);
-	}
-	if (nf_debug)
-		printk("Crap bits: 0x%04X", nf_debug);
-	printk("\n");
-}
-
-static void nf_dump_skb(int pf, struct sk_buff *skb)
-{
-	printk("skb: pf=%i %s dev=%s len=%u\n", 
-	       pf,
-	       skb->sk ? "(owned)" : "(unowned)",
-	       skb->dev ? skb->dev->name : "(no dev)",
-	       skb->len);
-	switch (pf) {
-	case PF_INET: {
-		const struct iphdr *ip = skb->nh.iph;
-		__u32 *opt = (__u32 *) (ip + 1);
-		int opti;
-		__u16 src_port = 0, dst_port = 0;
-
-		if (ip->protocol == IPPROTO_TCP
-		    || ip->protocol == IPPROTO_UDP) {
-			struct tcphdr *tcp=(struct tcphdr *)((__u32 *)ip+ip->ihl);
-			src_port = ntohs(tcp->source);
-			dst_port = ntohs(tcp->dest);
-		}
-	
-		printk("PROTO=%d %u.%u.%u.%u:%hu %u.%u.%u.%u:%hu"
-		       " L=%hu S=0x%2.2hX I=%hu F=0x%4.4hX T=%hu",
-		       ip->protocol, NIPQUAD(ip->saddr),
-		       src_port, NIPQUAD(ip->daddr),
-		       dst_port,
-		       ntohs(ip->tot_len), ip->tos, ntohs(ip->id),
-		       ntohs(ip->frag_off), ip->ttl);
-
-		for (opti = 0; opti < (ip->ihl - sizeof(struct iphdr) / 4); opti++)
-			printk(" O=0x%8.8X", *opt++);
-		printk("\n");
-	}
-	}
-}
-
-void nf_debug_ip_local_deliver(struct sk_buff *skb)
-{
-	/* If it's a loopback packet, it must have come through
-	 * NF_IP_LOCAL_OUT, NF_IP_RAW_INPUT, NF_IP_PRE_ROUTING and
-	 * NF_IP_LOCAL_IN.  Otherwise, must have gone through
-	 * NF_IP_RAW_INPUT and NF_IP_PRE_ROUTING.  */
-	if (!skb->dev) {
-		printk("ip_local_deliver: skb->dev is NULL.\n");
-	} else {
-		if (skb->nf_debug != ((1<<NF_IP_PRE_ROUTING)
-				      | (1<<NF_IP_LOCAL_IN))) {
-			printk("ip_local_deliver: bad skb: ");
-			debug_print_hooks_ip(skb->nf_debug);
-			nf_dump_skb(PF_INET, skb);
-		}
-	}
-}
-
-void nf_debug_ip_loopback_xmit(struct sk_buff *newskb)
-{
-	if (newskb->nf_debug != ((1 << NF_IP_LOCAL_OUT)
-				 | (1 << NF_IP_POST_ROUTING))) {
-		printk("ip_dev_loopback_xmit: bad owned skb = %p: ", 
-		       newskb);
-		debug_print_hooks_ip(newskb->nf_debug);
-		nf_dump_skb(PF_INET, newskb);
-	}
-}
-
-void nf_debug_ip_finish_output2(struct sk_buff *skb)
-{
-	/* If it's owned, it must have gone through the
-	 * NF_IP_LOCAL_OUT and NF_IP_POST_ROUTING.
-	 * Otherwise, must have gone through
-	 * NF_IP_PRE_ROUTING, NF_IP_FORWARD and NF_IP_POST_ROUTING.
-	 */
-	if (skb->sk) {
-		if (skb->nf_debug != ((1 << NF_IP_LOCAL_OUT)
-				      | (1 << NF_IP_POST_ROUTING))) {
-			printk("ip_finish_output: bad owned skb = %p: ", skb);
-			debug_print_hooks_ip(skb->nf_debug);
-			nf_dump_skb(PF_INET, skb);
-		}
-	} else {
-		if (skb->nf_debug != ((1 << NF_IP_PRE_ROUTING)
-				      | (1 << NF_IP_FORWARD)
-				      | (1 << NF_IP_POST_ROUTING))) {
-			/* Fragments, entunnelled packets, TCP RSTs
-                           generated by ipt_REJECT will have no
-                           owners, but still may be local */
-			if (skb->nf_debug != ((1 << NF_IP_LOCAL_OUT)
-					      | (1 << NF_IP_POST_ROUTING))){
-				printk("ip_finish_output:"
-				       " bad unowned skb = %p: ",skb);
-				debug_print_hooks_ip(skb->nf_debug);
-				nf_dump_skb(PF_INET, skb);
-			}
-		}
-	}
-}
-#endif /*CONFIG_NETFILTER_DEBUG*/
-
 /* Call get/setsockopt() */
 static int nf_sockopt(struct sock *sk, int pf, int val, 
 		      char __user *opt, int *len, int get)
@@ -488,14 +358,6 @@
 	/* We may already have this, but read-locks nest anyway */
 	rcu_read_lock();
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	if (unlikely((*pskb)->nf_debug & (1 << hook))) {
-		printk("nf_hook: hook %i already set.\n", hook);
-		nf_dump_skb(pf, *pskb);
-	}
-	(*pskb)->nf_debug |= (1 << hook);
-#endif
-
 	elem = &nf_hooks[pf][hook];
 next_hook:
 	verdict = nf_iterate(&nf_hooks[pf][hook], pskb, hook, indev,
diff --git a/net/core/skbuff.c b/net/core/skbuff.c
index f65b3de..6d68c03 100644
--- a/net/core/skbuff.c
+++ b/net/core/skbuff.c
@@ -365,9 +365,6 @@
 	C(nfct);
 	nf_conntrack_get(skb->nfct);
 	C(nfctinfo);
-#ifdef CONFIG_NETFILTER_DEBUG
-	C(nf_debug);
-#endif
 #ifdef CONFIG_BRIDGE_NETFILTER
 	C(nf_bridge);
 	nf_bridge_get(skb->nf_bridge);
@@ -432,9 +429,6 @@
 	new->nfct	= old->nfct;
 	nf_conntrack_get(old->nfct);
 	new->nfctinfo	= old->nfctinfo;
-#ifdef CONFIG_NETFILTER_DEBUG
-	new->nf_debug	= old->nf_debug;
-#endif
 #ifdef CONFIG_BRIDGE_NETFILTER
 	new->nf_bridge	= old->nf_bridge;
 	nf_bridge_get(old->nf_bridge);
diff --git a/net/ipv4/Kconfig b/net/ipv4/Kconfig
index 6d3e8b1..05107e0 100644
--- a/net/ipv4/Kconfig
+++ b/net/ipv4/Kconfig
@@ -1,6 +1,32 @@
 #
 # IP configuration
 #
+choice 
+	prompt "Choose IP: FIB lookup""
+	depends on INET
+	default IP_FIB_HASH
+
+config IP_FIB_HASH
+	bool "FIB_HASH"
+	---help---
+	Current FIB is very proven and good enough for most users.
+
+config IP_FIB_TRIE
+	bool "FIB_TRIE"
+	---help---
+	Use new experimental LC-trie as FIB lookup algoritm. 
+        This improves lookup performance
+	
+	LC-trie is described in:
+	
+ 	IP-address lookup using LC-tries. Stefan Nilsson and Gunnar Karlsson
+ 	IEEE Journal on Selected Areas in Communications, 17(6):1083-1092, June 1999
+	An experimental study of compression methods for dynamic tries
+ 	Stefan Nilsson and Matti Tikkanen. Algorithmica, 33(1):19-33, 2002.
+ 	http://www.nada.kth.se/~snilsson/public/papers/dyntrie2/
+       
+endchoice
+
 config IP_MULTICAST
 	bool "IP: multicasting"
 	depends on INET
diff --git a/net/ipv4/Makefile b/net/ipv4/Makefile
index 8b37962..65d57d8 100644
--- a/net/ipv4/Makefile
+++ b/net/ipv4/Makefile
@@ -7,8 +7,10 @@
 	     ip_output.o ip_sockglue.o \
 	     tcp.o tcp_input.o tcp_output.o tcp_timer.o tcp_ipv4.o tcp_minisocks.o \
 	     datagram.o raw.o udp.o arp.o icmp.o devinet.o af_inet.o igmp.o \
-	     sysctl_net_ipv4.o fib_frontend.o fib_semantics.o fib_hash.o
+	     sysctl_net_ipv4.o fib_frontend.o fib_semantics.o
 
+obj-$(CONFIG_IP_FIB_HASH) += fib_hash.o
+obj-$(CONFIG_IP_FIB_TRIE) += fib_trie.o
 obj-$(CONFIG_PROC_FS) += proc.o
 obj-$(CONFIG_IP_MULTIPLE_TABLES) += fib_rules.o
 obj-$(CONFIG_IP_MROUTE) += ipmr.o
diff --git a/net/ipv4/af_inet.c b/net/ipv4/af_inet.c
index 03942f1..658e797 100644
--- a/net/ipv4/af_inet.c
+++ b/net/ipv4/af_inet.c
@@ -1119,6 +1119,10 @@
 #ifdef CONFIG_PROC_FS
 extern int  fib_proc_init(void);
 extern void fib_proc_exit(void);
+#ifdef CONFIG_IP_FIB_TRIE
+extern int  fib_stat_proc_init(void);
+extern void fib_stat_proc_exit(void);
+#endif
 extern int  ip_misc_proc_init(void);
 extern int  raw_proc_init(void);
 extern void raw_proc_exit(void);
@@ -1139,11 +1143,19 @@
 		goto out_udp;
 	if (fib_proc_init())
 		goto out_fib;
+#ifdef CONFIG_IP_FIB_TRIE
+         if (fib_stat_proc_init())
+                 goto out_fib_stat;
+ #endif
 	if (ip_misc_proc_init())
 		goto out_misc;
 out:
 	return rc;
 out_misc:
+#ifdef CONFIG_IP_FIB_TRIE
+ 	fib_stat_proc_exit();
+out_fib_stat:
+#endif
 	fib_proc_exit();
 out_fib:
 	udp4_proc_exit();
diff --git a/net/ipv4/fib_trie.c b/net/ipv4/fib_trie.c
new file mode 100644
index 0000000..0671569
--- /dev/null
+++ b/net/ipv4/fib_trie.c
@@ -0,0 +1,2454 @@
+/*
+ *   This program is free software; you can redistribute it and/or
+ *   modify it under the terms of the GNU General Public License
+ *   as published by the Free Software Foundation; either version
+ *   2 of the License, or (at your option) any later version.
+ *
+ *   Robert Olsson <robert.olsson@its.uu.se> Uppsala Universitet
+ *     & Swedish University of Agricultural Sciences.
+ *
+ *   Jens Laas <jens.laas@data.slu.se> Swedish University of 
+ *     Agricultural Sciences.
+ * 
+ *   Hans Liss <hans.liss@its.uu.se>  Uppsala Universitet
+ *
+ * This work is based on the LPC-trie which is originally descibed in:
+ * 
+ * An experimental study of compression methods for dynamic tries
+ * Stefan Nilsson and Matti Tikkanen. Algorithmica, 33(1):19-33, 2002.
+ * http://www.nada.kth.se/~snilsson/public/papers/dyntrie2/
+ *
+ *
+ * IP-address lookup using LC-tries. Stefan Nilsson and Gunnar Karlsson
+ * IEEE Journal on Selected Areas in Communications, 17(6):1083-1092, June 1999
+ *
+ * Version:	$Id: fib_trie.c,v 1.3 2005/06/08 14:20:01 robert Exp $
+ *
+ *
+ * Code from fib_hash has been reused which includes the following header:
+ *
+ *
+ * INET		An implementation of the TCP/IP protocol suite for the LINUX
+ *		operating system.  INET is implemented using the  BSD Socket
+ *		interface as the means of communication with the user level.
+ *
+ *		IPv4 FIB: lookup engine and maintenance routines.
+ *
+ *
+ * Authors:	Alexey Kuznetsov, <kuznet@ms2.inr.ac.ru>
+ *
+ *		This program is free software; you can redistribute it and/or
+ *		modify it under the terms of the GNU General Public License
+ *		as published by the Free Software Foundation; either version
+ *		2 of the License, or (at your option) any later version.
+ */
+
+#define VERSION "0.323"
+
+#include <linux/config.h>
+#include <asm/uaccess.h>
+#include <asm/system.h>
+#include <asm/bitops.h>
+#include <linux/types.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/mm.h>
+#include <linux/string.h>
+#include <linux/socket.h>
+#include <linux/sockios.h>
+#include <linux/errno.h>
+#include <linux/in.h>
+#include <linux/inet.h>
+#include <linux/netdevice.h>
+#include <linux/if_arp.h>
+#include <linux/proc_fs.h>
+#include <linux/skbuff.h>
+#include <linux/netlink.h>
+#include <linux/init.h>
+#include <linux/list.h>
+#include <net/ip.h>
+#include <net/protocol.h>
+#include <net/route.h>
+#include <net/tcp.h>
+#include <net/sock.h>
+#include <net/ip_fib.h>
+#include "fib_lookup.h"
+
+#undef CONFIG_IP_FIB_TRIE_STATS
+#define MAX_CHILDS 16384
+
+#define EXTRACT(p, n, str) ((str)<<(p)>>(32-(n)))
+#define KEYLENGTH (8*sizeof(t_key))
+#define MASK_PFX(k, l) (((l)==0)?0:(k >> (KEYLENGTH-l)) << (KEYLENGTH-l))
+#define TKEY_GET_MASK(offset, bits) (((bits)==0)?0:((t_key)(-1) << (KEYLENGTH - bits) >> offset))
+
+static DEFINE_RWLOCK(fib_lock);
+
+typedef unsigned int t_key;
+
+#define T_TNODE 0
+#define T_LEAF  1
+#define NODE_TYPE_MASK	0x1UL
+#define NODE_PARENT(_node) \
+((struct tnode *)((_node)->_parent & ~NODE_TYPE_MASK))
+#define NODE_SET_PARENT(_node, _ptr) \
+((_node)->_parent = (((unsigned long)(_ptr)) | \
+                     ((_node)->_parent & NODE_TYPE_MASK)))
+#define NODE_INIT_PARENT(_node, _type) \
+((_node)->_parent = (_type))
+#define NODE_TYPE(_node) \
+((_node)->_parent & NODE_TYPE_MASK)
+
+#define IS_TNODE(n) (!(n->_parent & T_LEAF))
+#define IS_LEAF(n) (n->_parent & T_LEAF)
+
+struct node {
+        t_key key;
+	unsigned long _parent;
+};
+
+struct leaf {
+        t_key key;
+	unsigned long _parent;
+	struct hlist_head list;
+};
+
+struct leaf_info {
+	struct hlist_node hlist;
+	int plen;
+	struct list_head falh;
+};
+
+struct tnode {
+        t_key key;
+	unsigned long _parent;
+        unsigned short pos:5;        /* 2log(KEYLENGTH) bits needed */
+        unsigned short bits:5;       /* 2log(KEYLENGTH) bits needed */
+        unsigned short full_children;  /* KEYLENGTH bits needed */
+        unsigned short empty_children; /* KEYLENGTH bits needed */
+        struct node *child[0];
+};
+
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+struct trie_use_stats {
+	unsigned int gets;
+	unsigned int backtrack;
+	unsigned int semantic_match_passed;
+	unsigned int semantic_match_miss;
+	unsigned int null_node_hit;
+};
+#endif
+
+struct trie_stat {
+	unsigned int totdepth;
+	unsigned int maxdepth;
+	unsigned int tnodes;
+	unsigned int leaves;
+	unsigned int nullpointers;
+	unsigned int nodesizes[MAX_CHILDS];
+};    
+
+struct trie {
+        struct node *trie;
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+	struct trie_use_stats stats;
+#endif
+        int size;
+	unsigned int revision;
+};
+
+static int trie_debug = 0;
+
+static int tnode_full(struct tnode *tn, struct node *n);
+static void put_child(struct trie *t, struct tnode *tn, int i, struct node *n);
+static void tnode_put_child_reorg(struct tnode *tn, int i, struct node *n, int wasfull);
+static int tnode_child_length(struct tnode *tn);
+static struct node *resize(struct trie *t, struct tnode *tn);
+static struct tnode *inflate(struct trie *t, struct tnode *tn);
+static struct tnode *halve(struct trie *t, struct tnode *tn);
+static void tnode_free(struct tnode *tn);
+static void trie_dump_seq(struct seq_file *seq, struct trie *t);
+extern struct fib_alias *fib_find_alias(struct list_head *fah, u8 tos, u32 prio);
+extern int fib_detect_death(struct fib_info *fi, int order,
+                            struct fib_info **last_resort, int *last_idx, int *dflt);
+
+extern void rtmsg_fib(int event, u32 key, struct fib_alias *fa, int z, int tb_id,
+               struct nlmsghdr *n, struct netlink_skb_parms *req);
+
+static kmem_cache_t *fn_alias_kmem;
+static struct trie *trie_local = NULL, *trie_main = NULL;
+
+static void trie_bug(char *err)
+{
+	printk("Trie Bug: %s\n", err);
+	BUG();
+}
+
+static inline struct node *tnode_get_child(struct tnode *tn, int i) 
+{
+        if (i >=  1<<tn->bits) 
+                trie_bug("tnode_get_child");
+
+        return tn->child[i];
+}
+
+static inline int tnode_child_length(struct tnode *tn)
+{
+        return 1<<tn->bits;
+}
+
+/*
+  _________________________________________________________________
+  | i | i | i | i | i | i | i | N | N | N | S | S | S | S | S | C |
+  ----------------------------------------------------------------
+    0   1   2   3   4   5   6   7   8   9  10  11  12  13  14  15 
+
+  _________________________________________________________________
+  | C | C | C | u | u | u | u | u | u | u | u | u | u | u | u | u |
+  -----------------------------------------------------------------
+   16  17  18  19  20  21  22  23  24  25  26  27  28  29  30  31
+
+  tp->pos = 7
+  tp->bits = 3
+  n->pos = 15
+  n->bits=4
+  KEYLENGTH=32
+*/
+
+static inline t_key tkey_extract_bits(t_key a, int offset, int bits)
+{
+        if (offset < KEYLENGTH)
+		return ((t_key)(a << offset)) >> (KEYLENGTH - bits);
+        else
+		return 0;
+}
+
+static inline int tkey_equals(t_key a, t_key b)
+{
+  return a == b;
+}
+
+static inline int tkey_sub_equals(t_key a, int offset, int bits, t_key b)
+{
+     if (bits == 0 || offset >= KEYLENGTH)
+            return 1;
+        bits = bits > KEYLENGTH ? KEYLENGTH : bits;
+        return ((a ^ b) << offset) >> (KEYLENGTH - bits) == 0;
+}	
+
+static inline int tkey_mismatch(t_key a, int offset, t_key b)
+{
+	t_key diff = a ^ b;
+	int i = offset;
+
+	if(!diff) 
+	  return 0;
+	while((diff << i) >> (KEYLENGTH-1) == 0)
+		i++;
+	return i;
+}
+
+/* Candiate for fib_semantics */
+
+static void fn_free_alias(struct fib_alias *fa)
+{
+	fib_release_info(fa->fa_info);
+	kmem_cache_free(fn_alias_kmem, fa);
+}
+
+/*
+  To understand this stuff, an understanding of keys and all their bits is 
+  necessary. Every node in the trie has a key associated with it, but not 
+  all of the bits in that key are significant.
+
+  Consider a node 'n' and its parent 'tp'.
+
+  If n is a leaf, every bit in its key is significant. Its presence is 
+  necessitaded by path compression, since during a tree traversal (when 
+  searching for a leaf - unless we are doing an insertion) we will completely 
+  ignore all skipped bits we encounter. Thus we need to verify, at the end of 
+  a potentially successful search, that we have indeed been walking the 
+  correct key path.
+
+  Note that we can never "miss" the correct key in the tree if present by 
+  following the wrong path. Path compression ensures that segments of the key 
+  that are the same for all keys with a given prefix are skipped, but the 
+  skipped part *is* identical for each node in the subtrie below the skipped 
+  bit! trie_insert() in this implementation takes care of that - note the 
+  call to tkey_sub_equals() in trie_insert().
+
+  if n is an internal node - a 'tnode' here, the various parts of its key 
+  have many different meanings.
+
+  Example:  
+  _________________________________________________________________
+  | i | i | i | i | i | i | i | N | N | N | S | S | S | S | S | C |
+  -----------------------------------------------------------------
+    0   1   2   3   4   5   6   7   8   9  10  11  12  13  14  15 
+
+  _________________________________________________________________
+  | C | C | C | u | u | u | u | u | u | u | u | u | u | u | u | u |
+  -----------------------------------------------------------------
+   16  17  18  19  20  21  22  23  24  25  26  27  28  29  30  31
+
+  tp->pos = 7
+  tp->bits = 3
+  n->pos = 15
+  n->bits=4
+
+  First, let's just ignore the bits that come before the parent tp, that is 
+  the bits from 0 to (tp->pos-1). They are *known* but at this point we do 
+  not use them for anything.
+
+  The bits from (tp->pos) to (tp->pos + tp->bits - 1) - "N", above - are the
+  index into the parent's child array. That is, they will be used to find 
+  'n' among tp's children.
+
+  The bits from (tp->pos + tp->bits) to (n->pos - 1) - "S" - are skipped bits
+  for the node n.
+
+  All the bits we have seen so far are significant to the node n. The rest 
+  of the bits are really not needed or indeed known in n->key.
+
+  The bits from (n->pos) to (n->pos + n->bits - 1) - "C" - are the index into 
+  n's child array, and will of course be different for each child.
+  
+  The rest of the bits, from (n->pos + n->bits) onward, are completely unknown
+  at this point.
+
+*/
+
+static void check_tnode(struct tnode *tn)
+{
+	if(tn && tn->pos+tn->bits > 32) {
+		printk("TNODE ERROR tn=%p, pos=%d, bits=%d\n", tn, tn->pos, tn->bits);
+	}
+}
+
+static int halve_threshold = 25;
+static int inflate_threshold = 50;
+
+static struct leaf *leaf_new(void)
+{
+	struct leaf *l = kmalloc(sizeof(struct leaf),  GFP_KERNEL);
+	if(l) {
+		NODE_INIT_PARENT(l, T_LEAF);
+		INIT_HLIST_HEAD(&l->list);
+	}
+	return l;
+}
+
+static struct leaf_info *leaf_info_new(int plen)
+{
+	struct leaf_info *li = kmalloc(sizeof(struct leaf_info),  GFP_KERNEL);
+	li->plen = plen;
+	INIT_LIST_HEAD(&li->falh);
+	return li;
+}
+
+static inline void free_leaf(struct leaf *l)
+{
+	kfree(l);
+}
+
+static inline void free_leaf_info(struct leaf_info *li)
+{
+	kfree(li);
+}
+
+static struct tnode* tnode_new(t_key key, int pos, int bits)
+{
+	int nchildren = 1<<bits;
+	int sz = sizeof(struct tnode) + nchildren * sizeof(struct node *);
+	struct tnode *tn = kmalloc(sz,  GFP_KERNEL);
+
+	if(tn)  {
+		memset(tn, 0, sz);
+		NODE_INIT_PARENT(tn, T_TNODE);
+		tn->pos = pos;
+		tn->bits = bits;
+		tn->key = key;
+		tn->full_children = 0;
+		tn->empty_children = 1<<bits;
+	}
+	if(trie_debug > 0) 
+		printk("AT %p s=%u %u\n", tn, (unsigned int) sizeof(struct tnode),
+		       (unsigned int) (sizeof(struct node) * 1<<bits));
+	return tn;
+}
+
+static void tnode_free(struct tnode *tn)
+{
+	if(!tn) {
+		trie_bug("tnode_free\n");
+	}
+	if(IS_LEAF(tn)) {
+		free_leaf((struct leaf *)tn);
+		if(trie_debug > 0 ) 
+			printk("FL %p \n", tn);
+	}
+	else if(IS_TNODE(tn)) { 
+		kfree(tn);
+		if(trie_debug > 0 ) 
+			printk("FT %p \n", tn);
+	}
+	else {
+		trie_bug("tnode_free\n");
+	}
+}
+
+/*
+ * Check whether a tnode 'n' is "full", i.e. it is an internal node
+ * and no bits are skipped. See discussion in dyntree paper p. 6
+ */
+
+static inline int tnode_full(struct tnode *tn, struct node *n)
+{
+	if(n == NULL || IS_LEAF(n))
+		return 0;
+
+	return ((struct tnode *) n)->pos == tn->pos + tn->bits;
+}
+
+static inline void put_child(struct trie *t, struct tnode *tn, int i, struct node *n) 
+{
+	tnode_put_child_reorg(tn, i, n, -1);
+}
+
+ /* 
+  * Add a child at position i overwriting the old value.
+  * Update the value of full_children and empty_children.
+  */
+
+static void tnode_put_child_reorg(struct tnode *tn, int i, struct node *n, int wasfull) 
+{
+	struct node *chi;
+	int isfull;
+
+	if(i >=  1<<tn->bits) {
+		printk("bits=%d, i=%d\n", tn->bits, i);
+		trie_bug("tnode_put_child_reorg bits");
+	}
+	write_lock_bh(&fib_lock);
+	chi = tn->child[i];	
+
+	/* update emptyChildren */
+	if (n == NULL && chi != NULL)
+		tn->empty_children++;
+	else if (n != NULL && chi == NULL)
+		tn->empty_children--;
+  
+	/* update fullChildren */
+        if (wasfull == -1)
+		wasfull = tnode_full(tn, chi);
+
+	isfull = tnode_full(tn, n);
+	if (wasfull && !isfull) 
+		tn->full_children--;
+	
+	else if (!wasfull && isfull) 
+		tn->full_children++;
+	if(n) 
+		NODE_SET_PARENT(n, tn);	
+
+	tn->child[i] = n;
+	write_unlock_bh(&fib_lock);
+}
+
+static struct node *resize(struct trie *t, struct tnode *tn) 
+{
+	int i;
+
+ 	if (!tn)
+		return NULL;
+
+	if(trie_debug) 
+		printk("In tnode_resize %p inflate_threshold=%d threshold=%d\n", 
+		      tn, inflate_threshold, halve_threshold);
+
+	/* No children */
+	if (tn->empty_children == tnode_child_length(tn)) {
+		tnode_free(tn);
+		return NULL;
+	}
+	/* One child */
+	if (tn->empty_children == tnode_child_length(tn) - 1)
+		for (i = 0; i < tnode_child_length(tn); i++) {
+
+			write_lock_bh(&fib_lock);
+			if (tn->child[i] != NULL) {
+
+				/* compress one level */
+				struct node *n = tn->child[i];
+				if(n)
+					NODE_INIT_PARENT(n, NODE_TYPE(n));
+
+				write_unlock_bh(&fib_lock);
+				tnode_free(tn);
+				return n;
+			}
+			write_unlock_bh(&fib_lock);
+		}
+	/* 
+	 * Double as long as the resulting node has a number of
+	 * nonempty nodes that are above the threshold.
+	 */
+
+	/*
+	 * From "Implementing a dynamic compressed trie" by Stefan Nilsson of 
+	 * the Helsinki University of Technology and Matti Tikkanen of Nokia 
+	 * Telecommunications, page 6:
+	 * "A node is doubled if the ratio of non-empty children to all 
+	 * children in the *doubled* node is at least 'high'."
+	 *
+	 * 'high' in this instance is the variable 'inflate_threshold'. It 
+	 * is expressed as a percentage, so we multiply it with 
+	 * tnode_child_length() and instead of multiplying by 2 (since the 
+	 * child array will be doubled by inflate()) and multiplying 
+	 * the left-hand side by 100 (to handle the percentage thing) we 
+	 * multiply the left-hand side by 50.
+	 * 
+	 * The left-hand side may look a bit weird: tnode_child_length(tn) 
+	 * - tn->empty_children is of course the number of non-null children 
+	 * in the current node. tn->full_children is the number of "full" 
+	 * children, that is non-null tnodes with a skip value of 0.
+	 * All of those will be doubled in the resulting inflated tnode, so 
+	 * we just count them one extra time here.
+	 * 
+	 * A clearer way to write this would be:
+	 * 
+	 * to_be_doubled = tn->full_children;
+	 * not_to_be_doubled = tnode_child_length(tn) - tn->empty_children - 
+	 *     tn->full_children;
+	 *
+	 * new_child_length = tnode_child_length(tn) * 2;
+	 *
+	 * new_fill_factor = 100 * (not_to_be_doubled + 2*to_be_doubled) / 
+	 *      new_child_length;
+	 * if (new_fill_factor >= inflate_threshold)
+	 * 
+	 * ...and so on, tho it would mess up the while() loop.
+	 * 
+	 * anyway,
+	 * 100 * (not_to_be_doubled + 2*to_be_doubled) / new_child_length >=
+	 *      inflate_threshold
+	 * 
+	 * avoid a division:
+	 * 100 * (not_to_be_doubled + 2*to_be_doubled) >=
+	 *      inflate_threshold * new_child_length
+	 * 
+	 * expand not_to_be_doubled and to_be_doubled, and shorten:
+	 * 100 * (tnode_child_length(tn) - tn->empty_children + 
+	 *    tn->full_children ) >= inflate_threshold * new_child_length
+	 * 
+	 * expand new_child_length:
+	 * 100 * (tnode_child_length(tn) - tn->empty_children + 
+	 *    tn->full_children ) >=
+	 *      inflate_threshold * tnode_child_length(tn) * 2
+	 * 
+	 * shorten again:
+	 * 50 * (tn->full_children + tnode_child_length(tn) - 
+	 *    tn->empty_children ) >= inflate_threshold * 
+	 *    tnode_child_length(tn)
+	 * 
+	 */
+
+	check_tnode(tn);
+
+	while ((tn->full_children > 0 &&
+	       50 * (tn->full_children + tnode_child_length(tn) - tn->empty_children) >=
+				inflate_threshold * tnode_child_length(tn))) {
+
+		tn = inflate(t, tn);
+	}
+
+	check_tnode(tn);
+
+	/*
+	 * Halve as long as the number of empty children in this
+	 * node is above threshold.
+	 */
+	while (tn->bits > 1 &&
+	       100 * (tnode_child_length(tn) - tn->empty_children) <
+	       halve_threshold * tnode_child_length(tn))
+
+		tn = halve(t, tn);
+  
+	/* Only one child remains */
+
+	if (tn->empty_children == tnode_child_length(tn) - 1)
+		for (i = 0; i < tnode_child_length(tn); i++) {
+			
+			write_lock_bh(&fib_lock);
+			if (tn->child[i] != NULL) {
+				/* compress one level */
+				struct node *n = tn->child[i];
+
+				if(n)
+					NODE_INIT_PARENT(n, NODE_TYPE(n));
+
+				write_unlock_bh(&fib_lock);
+				tnode_free(tn);
+				return n;
+			}
+			write_unlock_bh(&fib_lock);
+		}
+
+	return (struct node *) tn;
+}
+
+static struct tnode *inflate(struct trie *t, struct tnode *tn)
+{
+	struct tnode *inode;
+	struct tnode *oldtnode = tn;
+	int olen = tnode_child_length(tn);
+	int i;
+
+  	if(trie_debug) 
+		printk("In inflate\n");
+
+	tn = tnode_new(oldtnode->key, oldtnode->pos, oldtnode->bits + 1);
+
+	if (!tn)
+		trie_bug("tnode_new failed");
+
+	for(i = 0; i < olen; i++) {
+		struct node *node = tnode_get_child(oldtnode, i);
+      
+		/* An empty child */
+		if (node == NULL)
+			continue;
+
+		/* A leaf or an internal node with skipped bits */
+
+		if(IS_LEAF(node) || ((struct tnode *) node)->pos >
+		   tn->pos + tn->bits - 1) {
+			if(tkey_extract_bits(node->key, tn->pos + tn->bits - 1,
+					     1) == 0)
+				put_child(t, tn, 2*i, node);
+			else
+				put_child(t, tn, 2*i+1, node);
+			continue;
+		}
+
+		/* An internal node with two children */
+		inode = (struct tnode *) node;
+
+		if (inode->bits == 1) {
+			put_child(t, tn, 2*i, inode->child[0]);
+			put_child(t, tn, 2*i+1, inode->child[1]);
+
+			tnode_free(inode);
+		}
+
+			/* An internal node with more than two children */
+		else {
+			struct tnode *left, *right;
+			int size, j;
+
+			/* We will replace this node 'inode' with two new 
+			 * ones, 'left' and 'right', each with half of the 
+			 * original children. The two new nodes will have 
+			 * a position one bit further down the key and this 
+			 * means that the "significant" part of their keys 
+			 * (see the discussion near the top of this file) 
+			 * will differ by one bit, which will be "0" in 
+			 * left's key and "1" in right's key. Since we are 
+			 * moving the key position by one step, the bit that 
+			 * we are moving away from - the bit at position 
+			 * (inode->pos) - is the one that will differ between 
+			 * left and right. So... we synthesize that bit in the
+			 * two  new keys.
+			 * The mask 'm' below will be a single "one" bit at 
+			 * the position (inode->pos)
+			 */
+
+			t_key m = TKEY_GET_MASK(inode->pos, 1);
+ 
+			/* Use the old key, but set the new significant 
+			 *   bit to zero. 
+			 */
+			left = tnode_new(inode->key&(~m), inode->pos + 1,
+					 inode->bits - 1);
+
+			if(!left) 
+				trie_bug("tnode_new failed");
+			
+			
+			/* Use the old key, but set the new significant 
+			 * bit to one. 
+			 */
+			right = tnode_new(inode->key|m, inode->pos + 1,
+					  inode->bits - 1);
+
+			if(!right) 
+				trie_bug("tnode_new failed");
+			
+			size = tnode_child_length(left);
+			for(j = 0; j < size; j++) {
+				put_child(t, left, j, inode->child[j]);
+				put_child(t, right, j, inode->child[j + size]);
+			}
+			put_child(t, tn, 2*i, resize(t, left));
+			put_child(t, tn, 2*i+1, resize(t, right));
+
+			tnode_free(inode);
+		}
+	}
+	tnode_free(oldtnode);
+	return tn;
+}
+
+static struct tnode *halve(struct trie *t, struct tnode *tn)
+{
+	struct tnode *oldtnode = tn;
+	struct node *left, *right;
+	int i;
+	int olen = tnode_child_length(tn);
+
+	if(trie_debug) printk("In halve\n");
+  
+	tn=tnode_new(oldtnode->key, oldtnode->pos, oldtnode->bits - 1);
+
+	if(!tn) 
+		trie_bug("tnode_new failed");
+
+	for(i = 0; i < olen; i += 2) {
+		left = tnode_get_child(oldtnode, i);
+		right = tnode_get_child(oldtnode, i+1);
+    
+		/* At least one of the children is empty */
+		if (left == NULL) {
+			if (right == NULL)    /* Both are empty */
+				continue;
+			put_child(t, tn, i/2, right);
+		} else if (right == NULL)
+			put_child(t, tn, i/2, left);
+     
+		/* Two nonempty children */
+		else {
+			struct tnode *newBinNode =
+				tnode_new(left->key, tn->pos + tn->bits, 1);
+
+			if(!newBinNode) 
+				trie_bug("tnode_new failed");
+
+			put_child(t, newBinNode, 0, left);
+			put_child(t, newBinNode, 1, right);
+			put_child(t, tn, i/2, resize(t, newBinNode));
+		}
+	}
+	tnode_free(oldtnode);
+	return tn;
+}
+
+static void *trie_init(struct trie *t)
+{
+	if(t) {
+		t->size = 0;
+		t->trie = NULL;
+		t->revision = 0;
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+       		memset(&t->stats, 0, sizeof(struct trie_use_stats));
+#endif
+	}
+	return t;
+}
+
+static struct leaf_info *find_leaf_info(struct hlist_head *head, int plen)
+{
+	struct hlist_node *node;
+	struct leaf_info *li;
+
+	hlist_for_each_entry(li, node, head, hlist) {
+		  
+		if ( li->plen == plen )
+			return li;
+	}
+	return NULL;
+}
+
+static inline struct list_head * get_fa_head(struct leaf *l, int plen)
+{
+	struct list_head *fa_head=NULL;
+	struct leaf_info *li = find_leaf_info(&l->list, plen);
+	
+	if(li) 
+		fa_head = &li->falh;
+	
+	return fa_head;
+}
+
+static void insert_leaf_info(struct hlist_head *head, struct leaf_info *new)
+{
+	struct leaf_info *li=NULL, *last=NULL;
+	struct hlist_node *node, *tmp;
+
+	write_lock_bh(&fib_lock);
+	
+	if(hlist_empty(head))
+		hlist_add_head(&new->hlist, head);
+	else {
+		hlist_for_each_entry_safe(li, node, tmp, head, hlist) {
+			
+			if (new->plen > li->plen) 
+				break;
+			
+			last = li;
+		}
+		if(last) 
+			hlist_add_after(&last->hlist, &new->hlist);
+		else 
+			hlist_add_before(&new->hlist, &li->hlist);
+	}
+	write_unlock_bh(&fib_lock);
+}
+
+static struct leaf *
+fib_find_node(struct trie *t, u32 key)
+{
+	int pos;
+	struct tnode *tn;
+	struct node *n;
+
+	pos = 0;
+	n=t->trie;
+
+	while (n != NULL &&  NODE_TYPE(n) == T_TNODE) {
+		tn = (struct tnode *) n;
+			
+		check_tnode(tn);
+			
+		if(tkey_sub_equals(tn->key, pos, tn->pos-pos, key)) {
+			pos=tn->pos + tn->bits;
+			n = tnode_get_child(tn, tkey_extract_bits(key, tn->pos, tn->bits));
+		}
+		else
+			break;
+	}
+	/* Case we have found a leaf. Compare prefixes */
+
+	if (n != NULL && IS_LEAF(n) && tkey_equals(key, n->key)) {
+		struct leaf *l = (struct leaf *) n;
+		return l;
+	}
+	return NULL;
+}
+
+static struct node *trie_rebalance(struct trie *t, struct tnode *tn)
+{
+	int i = 0;
+	int wasfull;
+	t_key cindex, key;
+	struct tnode *tp = NULL;
+
+	if(!tn) 
+		BUG();
+	
+	key = tn->key;
+	i = 0;
+
+	while (tn != NULL && NODE_PARENT(tn) != NULL) {
+
+		if( i > 10 ) {
+			printk("Rebalance tn=%p \n", tn);
+			if(tn) 		printk("tn->parent=%p \n", NODE_PARENT(tn));
+			
+			printk("Rebalance tp=%p \n", tp);
+			if(tp) 		printk("tp->parent=%p \n", NODE_PARENT(tp));
+		}
+
+		if( i > 12 ) BUG();
+		i++;
+
+		tp = NODE_PARENT(tn);
+		cindex = tkey_extract_bits(key, tp->pos, tp->bits);
+		wasfull = tnode_full(tp, tnode_get_child(tp, cindex));
+		tn = (struct tnode *) resize (t, (struct tnode *)tn);
+		tnode_put_child_reorg((struct tnode *)tp, cindex,(struct node*)tn, wasfull);
+		
+		if(!NODE_PARENT(tn))
+			break;
+
+		tn = NODE_PARENT(tn);
+	}
+	/* Handle last (top) tnode */
+	if (IS_TNODE(tn)) 
+		tn = (struct tnode*) resize(t, (struct tnode *)tn);
+
+	return (struct node*) tn;
+}
+
+static struct list_head *
+fib_insert_node(struct trie *t, u32 key, int plen)
+{
+	int pos, newpos;
+	struct tnode *tp = NULL, *tn = NULL;
+	struct node *n;
+	struct leaf *l;
+	int missbit;
+	struct list_head *fa_head=NULL;
+	struct leaf_info *li;
+	t_key cindex;
+
+	pos = 0;
+	n=t->trie;
+
+	/* If we point to NULL, stop. Either the tree is empty and we should 
+	 * just put a new leaf in if, or we have reached an empty child slot, 
+	 * and we should just put our new leaf in that.
+	 * If we point to a T_TNODE, check if it matches our key. Note that 
+	 * a T_TNODE might be skipping any number of bits - its 'pos' need 
+	 * not be the parent's 'pos'+'bits'!
+	 *
+	 * If it does match the current key, get pos/bits from it, extract 
+	 * the index from our key, push the T_TNODE and walk the tree.
+	 *
+	 * If it doesn't, we have to replace it with a new T_TNODE.
+	 *
+	 * If we point to a T_LEAF, it might or might not have the same key 
+	 * as we do. If it does, just change the value, update the T_LEAF's 
+	 * value, and return it. 
+	 * If it doesn't, we need to replace it with a T_TNODE.
+	 */
+
+	while (n != NULL &&  NODE_TYPE(n) == T_TNODE) {
+		tn = (struct tnode *) n;
+			
+		check_tnode(tn);
+		
+		if(tkey_sub_equals(tn->key, pos, tn->pos-pos, key)) {
+			tp = tn;
+			pos=tn->pos + tn->bits;
+			n = tnode_get_child(tn, tkey_extract_bits(key, tn->pos, tn->bits));
+
+			if(n && NODE_PARENT(n) != tn) {
+				printk("BUG tn=%p, n->parent=%p\n", tn, NODE_PARENT(n));
+				BUG();
+			}
+		}
+		else
+			break;
+	}
+
+	/*
+	 * n  ----> NULL, LEAF or TNODE
+	 *
+	 * tp is n's (parent) ----> NULL or TNODE  
+	 */
+
+	if(tp && IS_LEAF(tp))
+		BUG();
+
+	t->revision++;
+
+	/* Case 1: n is a leaf. Compare prefixes */
+
+	if (n != NULL && IS_LEAF(n) && tkey_equals(key, n->key)) { 
+		struct leaf *l = ( struct leaf *)  n;
+		
+		li = leaf_info_new(plen);
+		
+		if(! li) 
+			BUG();
+
+		fa_head = &li->falh;
+		insert_leaf_info(&l->list, li);
+		goto done;
+	}
+	t->size++;
+	l = leaf_new();
+
+	if(! l) 
+		BUG();
+
+	l->key = key;
+	li = leaf_info_new(plen);
+
+	if(! li) 
+		BUG();
+
+	fa_head = &li->falh;
+	insert_leaf_info(&l->list, li);
+
+	/* Case 2: n is NULL, and will just insert a new leaf */
+	if (t->trie && n == NULL) {
+
+		NODE_SET_PARENT(l, tp);
+		
+		if (!tp) 
+			BUG();
+
+		else {
+			cindex = tkey_extract_bits(key, tp->pos, tp->bits);
+			put_child(t, (struct tnode *)tp, cindex, (struct node *)l);
+		}
+	}
+	/* Case 3: n is a LEAF or a TNODE and the key doesn't match. */
+	else {
+		/* 
+		 *  Add a new tnode here 
+		 *  first tnode need some special handling
+		 */
+
+		if (tp)
+			pos=tp->pos+tp->bits;
+		else
+			pos=0;
+		if(n) {
+			newpos = tkey_mismatch(key, pos, n->key);
+			tn = tnode_new(n->key, newpos, 1);
+		}
+		else {
+			newpos = 0;
+			tn = tnode_new(key, newpos, 1); /* First tnode */ 
+		}
+		if(!tn) 
+			trie_bug("tnode_pfx_new failed");
+
+		NODE_SET_PARENT(tn, tp);
+
+		missbit=tkey_extract_bits(key, newpos, 1);
+		put_child(t, tn, missbit, (struct node *)l);
+		put_child(t, tn, 1-missbit, n);
+
+		if(tp) {
+			cindex = tkey_extract_bits(key, tp->pos, tp->bits);
+			put_child(t, (struct tnode *)tp, cindex, (struct node *)tn);
+		}
+		else { 
+			t->trie = (struct node*) tn; /* First tnode */
+			tp = tn;
+		}
+	}
+	if(tp && tp->pos+tp->bits > 32) {
+		printk("ERROR tp=%p pos=%d, bits=%d, key=%0x plen=%d\n", 
+		       tp, tp->pos, tp->bits, key, plen);
+	}
+	/* Rebalance the trie */
+	t->trie = trie_rebalance(t, tp);
+done:;
+	return fa_head;
+}
+
+static int
+fn_trie_insert(struct fib_table *tb, struct rtmsg *r, struct kern_rta *rta,
+	       struct nlmsghdr *nlhdr, struct netlink_skb_parms *req)
+{
+	struct trie *t = (struct trie *) tb->tb_data;
+	struct fib_alias *fa, *new_fa;
+	struct list_head *fa_head=NULL;
+	struct fib_info *fi;
+	int plen = r->rtm_dst_len;
+	int type = r->rtm_type;
+	u8 tos = r->rtm_tos;
+	u32 key, mask;
+	int err;
+	struct leaf *l;
+
+	if (plen > 32)
+		return -EINVAL;
+
+	key = 0;
+	if (rta->rta_dst) 
+		memcpy(&key, rta->rta_dst, 4);
+
+	key = ntohl(key);
+
+	if(trie_debug)
+		printk("Insert table=%d %08x/%d\n", tb->tb_id, key, plen);
+
+	mask =  ntohl( inet_make_mask(plen) );
+
+	if(key & ~mask)
+		return -EINVAL;
+
+	key = key & mask;
+
+	if  ((fi = fib_create_info(r, rta, nlhdr, &err)) == NULL)
+		goto err;
+
+	l = fib_find_node(t, key);
+	fa = NULL;	
+
+	if(l) {
+		fa_head = get_fa_head(l, plen);
+		fa = fib_find_alias(fa_head, tos, fi->fib_priority);
+	}
+
+	/* Now fa, if non-NULL, points to the first fib alias
+	 * with the same keys [prefix,tos,priority], if such key already
+	 * exists or to the node before which we will insert new one.
+	 *
+	 * If fa is NULL, we will need to allocate a new one and
+	 * insert to the head of f.
+	 *
+	 * If f is NULL, no fib node matched the destination key
+	 * and we need to allocate a new one of those as well.
+	 */
+
+	if (fa &&
+	    fa->fa_info->fib_priority == fi->fib_priority) {
+		struct fib_alias *fa_orig;
+
+		err = -EEXIST;
+		if (nlhdr->nlmsg_flags & NLM_F_EXCL)
+			goto out;
+
+		if (nlhdr->nlmsg_flags & NLM_F_REPLACE) {
+			struct fib_info *fi_drop;
+			u8 state;
+
+			write_lock_bh(&fib_lock);
+
+			fi_drop = fa->fa_info;
+			fa->fa_info = fi;
+			fa->fa_type = type;
+			fa->fa_scope = r->rtm_scope;
+			state = fa->fa_state;
+			fa->fa_state &= ~FA_S_ACCESSED;
+
+			write_unlock_bh(&fib_lock);
+
+			fib_release_info(fi_drop);
+			if (state & FA_S_ACCESSED)
+			  rt_cache_flush(-1);
+
+			    goto succeeded;
+		}
+		/* Error if we find a perfect match which
+		 * uses the same scope, type, and nexthop
+		 * information.
+		 */
+		fa_orig = fa;
+		list_for_each_entry(fa, fa_orig->fa_list.prev, fa_list) {
+			if (fa->fa_tos != tos)
+				break;
+			if (fa->fa_info->fib_priority != fi->fib_priority)
+				break;
+			if (fa->fa_type == type &&
+			    fa->fa_scope == r->rtm_scope &&
+			    fa->fa_info == fi) {
+				goto out;
+			}
+		}
+		if (!(nlhdr->nlmsg_flags & NLM_F_APPEND))
+			fa = fa_orig;
+	}
+	err = -ENOENT;
+	if (!(nlhdr->nlmsg_flags&NLM_F_CREATE))
+		goto out;
+
+	err = -ENOBUFS;
+	new_fa = kmem_cache_alloc(fn_alias_kmem, SLAB_KERNEL);
+	if (new_fa == NULL)
+		goto out;
+
+	new_fa->fa_info = fi;
+	new_fa->fa_tos = tos;
+	new_fa->fa_type = type;
+	new_fa->fa_scope = r->rtm_scope;
+	new_fa->fa_state = 0;
+#if 0
+	new_fa->dst  = NULL;
+#endif
+	/*
+	 * Insert new entry to the list.
+	 */
+
+	if(!fa_head)
+		fa_head = fib_insert_node(t, key, plen);
+
+	write_lock_bh(&fib_lock);
+
+	list_add_tail(&new_fa->fa_list,
+		 (fa ? &fa->fa_list : fa_head));
+
+	write_unlock_bh(&fib_lock);
+
+	rt_cache_flush(-1);
+	rtmsg_fib(RTM_NEWROUTE, htonl(key), new_fa, plen, tb->tb_id, nlhdr, req);
+succeeded:
+	return 0;
+out:
+	fib_release_info(fi);
+err:;	
+	return err;
+}
+
+static inline int check_leaf(struct trie *t, struct leaf *l,  t_key key, int *plen, const struct flowi *flp, 
+			     struct fib_result *res, int *err)
+{
+	int i;
+	t_key mask;
+	struct leaf_info *li;
+	struct hlist_head *hhead = &l->list;
+	struct hlist_node *node;
+	
+	hlist_for_each_entry(li, node, hhead, hlist) {
+
+		i = li->plen;
+		mask = ntohl(inet_make_mask(i));
+		if (l->key != (key & mask)) 
+			continue;
+
+		if (((*err) = fib_semantic_match(&li->falh, flp, res, l->key, mask, i)) == 0) {
+			*plen = i;
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+			t->stats.semantic_match_passed++;
+#endif
+			return 1;
+		}
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+		t->stats.semantic_match_miss++;
+#endif
+	}
+	return 0;
+}
+
+static int
+fn_trie_lookup(struct fib_table *tb, const struct flowi *flp, struct fib_result *res)
+{
+	struct trie *t = (struct trie *) tb->tb_data;
+	int plen, ret = 0;
+	struct node *n;
+	struct tnode *pn;
+	int pos, bits;
+	t_key key=ntohl(flp->fl4_dst);
+	int chopped_off;
+	t_key cindex = 0;
+	int current_prefix_length = KEYLENGTH;
+	n = t->trie;
+
+	read_lock(&fib_lock);
+	if(!n)
+		goto failed;
+
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+	t->stats.gets++;
+#endif
+
+	/* Just a leaf? */
+	if (IS_LEAF(n)) {
+		if( check_leaf(t, (struct leaf *)n, key, &plen, flp, res, &ret) )
+			goto found;
+		goto failed;
+	}
+	pn = (struct tnode *) n;
+	chopped_off = 0;
+	
+        while (pn) {
+
+		pos = pn->pos;
+		bits = pn->bits;
+
+		if(!chopped_off) 
+			cindex = tkey_extract_bits(MASK_PFX(key, current_prefix_length), pos, bits);
+
+		n = tnode_get_child(pn, cindex);
+
+		if (n == NULL) {
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+			t->stats.null_node_hit++;
+#endif
+			goto backtrace;
+		}
+
+		if (IS_TNODE(n)) {
+#define HL_OPTIMIZE
+#ifdef HL_OPTIMIZE
+			struct tnode *cn = (struct tnode *)n;
+			t_key node_prefix, key_prefix, pref_mismatch;
+			int mp;
+
+			/*
+			 * It's a tnode, and we can do some extra checks here if we 
+			 * like, to avoid descending into a dead-end branch.
+			 * This tnode is in the parent's child array at index 
+			 * key[p_pos..p_pos+p_bits] but potentially with some bits 
+			 * chopped off, so in reality the index may be just a 
+			 * subprefix, padded with zero at the end.
+			 * We can also take a look at any skipped bits in this 
+			 * tnode - everything up to p_pos is supposed to be ok, 
+			 * and the non-chopped bits of the index (se previous
+			 * paragraph) are also guaranteed ok, but the rest is 
+			 * considered unknown.
+			 *
+			 * The skipped bits are key[pos+bits..cn->pos].
+			 */
+			
+			/* If current_prefix_length < pos+bits, we are already doing 
+			 * actual prefix  matching, which means everything from 
+			 * pos+(bits-chopped_off) onward must be zero along some 
+			 * branch of this subtree - otherwise there is *no* valid 
+			 * prefix present. Here we can only check the skipped
+			 * bits. Remember, since we have already indexed into the 
+			 * parent's child array, we know that the bits we chopped of 
+			 * *are* zero.
+			 */
+
+			/* NOTA BENE: CHECKING ONLY SKIPPED BITS FOR THE NEW NODE HERE */
+			
+			if (current_prefix_length < pos+bits) {
+				if (tkey_extract_bits(cn->key, current_prefix_length,
+						      cn->pos - current_prefix_length) != 0 ||
+				    !(cn->child[0]))
+					goto backtrace;
+			}
+
+			/*
+			 * If chopped_off=0, the index is fully validated and we 
+			 * only need to look at the skipped bits for this, the new, 
+			 * tnode. What we actually want to do is to find out if
+			 * these skipped bits match our key perfectly, or if we will
+			 * have to count on finding a matching prefix further down, 
+			 * because if we do, we would like to have some way of 
+			 * verifying the existence of such a prefix at this point. 
+			 */
+
+			/* The only thing we can do at this point is to verify that
+			 * any such matching prefix can indeed be a prefix to our
+			 * key, and if the bits in the node we are inspecting that
+			 * do not match our key are not ZERO, this cannot be true.
+			 * Thus, find out where there is a mismatch (before cn->pos)
+			 * and verify that all the mismatching bits are zero in the
+			 * new tnode's key.
+			 */
+
+			/* Note: We aren't very concerned about the piece of the key 
+			 * that precede pn->pos+pn->bits, since these have already been 
+			 * checked. The bits after cn->pos aren't checked since these are 
+			 * by definition "unknown" at this point. Thus, what we want to 
+			 * see is if we are about to enter the "prefix matching" state, 
+			 * and in that case verify that the skipped bits that will prevail 
+			 * throughout this subtree are zero, as they have to be if we are 
+			 * to find a matching prefix.
+			 */
+
+			node_prefix = MASK_PFX(cn->key, cn->pos);
+			key_prefix =  MASK_PFX(key, cn->pos);
+			pref_mismatch = key_prefix^node_prefix;
+			mp = 0;
+
+			/* In short: If skipped bits in this node do not match the search 
+			 * key, enter the "prefix matching" state.directly.
+			 */
+			if (pref_mismatch) {
+				while (!(pref_mismatch & (1<<(KEYLENGTH-1)))) {
+					mp++;
+					pref_mismatch = pref_mismatch <<1;
+				}
+				key_prefix = tkey_extract_bits(cn->key, mp, cn->pos-mp);
+				
+				if (key_prefix != 0)
+					goto backtrace;
+
+				if (current_prefix_length >= cn->pos)
+					current_prefix_length=mp;
+		       }
+#endif
+		       pn = (struct tnode *)n; /* Descend */
+		       chopped_off = 0;
+		       continue;
+		} 
+		if (IS_LEAF(n)) {	
+			if( check_leaf(t, (struct leaf *)n, key, &plen, flp, res, &ret))
+				goto found;
+	       }
+backtrace:
+		chopped_off++;
+
+		/* As zero don't change the child key (cindex) */
+		while ((chopped_off <= pn->bits) && !(cindex & (1<<(chopped_off-1)))) {
+			chopped_off++;
+		}
+
+		/* Decrease current_... with bits chopped off */
+		if (current_prefix_length > pn->pos + pn->bits - chopped_off)
+			current_prefix_length = pn->pos + pn->bits - chopped_off;
+		
+		/*
+		 * Either we do the actual chop off according or if we have 
+		 * chopped off all bits in this tnode walk up to our parent.
+		 */
+
+		if(chopped_off <= pn->bits)
+			cindex &= ~(1 << (chopped_off-1));
+		else {
+			if( NODE_PARENT(pn) == NULL)
+				goto failed;
+			
+			/* Get Child's index */
+			cindex = tkey_extract_bits(pn->key, NODE_PARENT(pn)->pos, NODE_PARENT(pn)->bits);
+			pn = NODE_PARENT(pn);
+			chopped_off = 0;
+
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+			t->stats.backtrack++;
+#endif
+			goto backtrace;
+		} 
+	}
+failed:
+	ret =  1;
+found:
+	read_unlock(&fib_lock);
+	return ret;
+}
+
+static int trie_leaf_remove(struct trie *t, t_key key)
+{
+	t_key cindex;
+	struct tnode *tp = NULL;
+	struct node *n = t->trie;
+	struct leaf *l;
+
+	if(trie_debug) 
+		printk("entering trie_leaf_remove(%p)\n", n);
+
+	/* Note that in the case skipped bits, those bits are *not* checked!
+	 * When we finish this, we will have NULL or a T_LEAF, and the 
+	 * T_LEAF may or may not match our key.
+	 */
+
+        while (n != NULL && IS_TNODE(n)) {
+		struct tnode *tn = (struct tnode *) n;
+		check_tnode(tn);
+		n = tnode_get_child(tn ,tkey_extract_bits(key, tn->pos, tn->bits));
+
+			if(n && NODE_PARENT(n) != tn) {
+				printk("BUG tn=%p, n->parent=%p\n", tn, NODE_PARENT(n));
+				BUG();
+			}
+        }
+	l = (struct leaf *) n;
+
+	if(!n || !tkey_equals(l->key, key)) 
+		return 0;
+    
+	/* 
+	 * Key found. 
+	 * Remove the leaf and rebalance the tree 
+	 */
+
+	t->revision++;
+	t->size--;
+
+	tp = NODE_PARENT(n);
+	tnode_free((struct tnode *) n);
+
+	if(tp) {
+		cindex = tkey_extract_bits(key, tp->pos, tp->bits);
+		put_child(t, (struct tnode *)tp, cindex, NULL);
+		t->trie = trie_rebalance(t, tp);
+	}
+	else
+		t->trie = NULL;
+
+	return 1;
+}
+
+static int
+fn_trie_delete(struct fib_table *tb, struct rtmsg *r, struct kern_rta *rta,
+	       struct nlmsghdr *nlhdr, struct netlink_skb_parms *req)
+{
+	struct trie *t = (struct trie *) tb->tb_data;
+	u32 key, mask;
+	int plen = r->rtm_dst_len;
+	u8 tos = r->rtm_tos;
+	struct fib_alias *fa, *fa_to_delete;
+	struct list_head *fa_head;
+	struct leaf *l;
+
+	if (plen > 32) 
+		return -EINVAL;
+
+	key = 0;
+	if (rta->rta_dst) 
+		memcpy(&key, rta->rta_dst, 4);
+
+	key = ntohl(key);
+	mask =  ntohl( inet_make_mask(plen) );
+
+	if(key & ~mask)
+		return -EINVAL;
+
+	key = key & mask;
+	l = fib_find_node(t, key);
+
+	if(!l)
+		return -ESRCH;
+
+	fa_head = get_fa_head(l, plen);
+	fa = fib_find_alias(fa_head, tos, 0);
+
+	if (!fa)
+		return -ESRCH;
+
+	if (trie_debug)
+		printk("Deleting %08x/%d tos=%d t=%p\n", key, plen, tos, t);
+
+	fa_to_delete = NULL;
+	fa_head = fa->fa_list.prev;
+	list_for_each_entry(fa, fa_head, fa_list) {
+		struct fib_info *fi = fa->fa_info;
+
+		if (fa->fa_tos != tos)
+			break;
+
+		if ((!r->rtm_type ||
+		     fa->fa_type == r->rtm_type) &&
+		    (r->rtm_scope == RT_SCOPE_NOWHERE ||
+		     fa->fa_scope == r->rtm_scope) &&
+		    (!r->rtm_protocol ||
+		     fi->fib_protocol == r->rtm_protocol) &&
+		    fib_nh_match(r, nlhdr, rta, fi) == 0) {
+			fa_to_delete = fa;
+			break;
+		}
+	}
+
+	if (fa_to_delete) {
+		int kill_li = 0;
+		struct leaf_info *li;
+
+		fa = fa_to_delete;
+		rtmsg_fib(RTM_DELROUTE, htonl(key), fa, plen, tb->tb_id, nlhdr, req);
+
+		l = fib_find_node(t, key);
+		li = find_leaf_info(&l->list, plen);
+
+		write_lock_bh(&fib_lock);
+
+		list_del(&fa->fa_list);
+
+		if(list_empty(fa_head)) {
+			hlist_del(&li->hlist);
+			kill_li = 1;
+		}
+		write_unlock_bh(&fib_lock);
+		
+		if(kill_li)
+			free_leaf_info(li);
+
+		if(hlist_empty(&l->list))
+			trie_leaf_remove(t, key);
+
+		if (fa->fa_state & FA_S_ACCESSED)
+			rt_cache_flush(-1);
+
+		fn_free_alias(fa);
+		return 0;
+	}
+	return -ESRCH;
+}
+
+static int trie_flush_list(struct trie *t, struct list_head *head)
+{
+	struct fib_alias *fa, *fa_node;
+	int found = 0;
+
+	list_for_each_entry_safe(fa, fa_node, head, fa_list) {
+		struct fib_info *fi = fa->fa_info;
+		
+		if (fi && (fi->fib_flags&RTNH_F_DEAD)) {
+
+ 			write_lock_bh(&fib_lock);	
+			list_del(&fa->fa_list);
+			write_unlock_bh(&fib_lock); 
+
+			fn_free_alias(fa);
+			found++;
+		}
+	}
+	return found;
+}
+
+static int trie_flush_leaf(struct trie *t, struct leaf *l)
+{
+	int found = 0;
+	struct hlist_head *lih = &l->list;
+	struct hlist_node *node, *tmp;
+	struct leaf_info *li = NULL;
+
+	hlist_for_each_entry_safe(li, node, tmp, lih, hlist) {
+			
+		found += trie_flush_list(t, &li->falh);
+
+		if (list_empty(&li->falh)) {
+
+ 			write_lock_bh(&fib_lock); 
+			hlist_del(&li->hlist);
+			write_unlock_bh(&fib_lock); 
+
+			free_leaf_info(li);
+		}
+	}
+	return found;
+}
+
+static struct leaf *nextleaf(struct trie *t, struct leaf *thisleaf)
+{
+	struct node *c = (struct node *) thisleaf;
+	struct tnode *p;
+	int idx;
+
+	if(c == NULL) {
+		if(t->trie == NULL)
+			return NULL;
+
+		if (IS_LEAF(t->trie))          /* trie w. just a leaf */
+			return (struct leaf *) t->trie;
+
+		p = (struct tnode*) t->trie;  /* Start */
+	}
+	else 
+		p = (struct tnode *) NODE_PARENT(c);
+	while (p) {
+		int pos, last;
+
+		/*  Find the next child of the parent */
+		if(c)
+			pos  = 1 + tkey_extract_bits(c->key, p->pos, p->bits);
+		else 
+			pos = 0;
+
+		last = 1 << p->bits;
+		for(idx = pos; idx < last ; idx++) {
+			if( p->child[idx]) {
+
+				/* Decend if tnode */
+
+				while (IS_TNODE(p->child[idx])) {
+					p = (struct tnode*) p->child[idx];
+					idx = 0;
+					
+					/* Rightmost non-NULL branch */
+					if( p && IS_TNODE(p) )
+						while ( p->child[idx] == NULL && idx < (1 << p->bits) ) idx++;
+
+					/* Done with this tnode? */
+					if( idx >= (1 << p->bits) || p->child[idx] == NULL ) 
+						goto up;
+				}
+				return (struct leaf*) p->child[idx];
+			}
+		}
+up:
+		/* No more children go up one step  */
+		c = (struct node*) p;
+		p = (struct tnode *) NODE_PARENT(p);
+	}
+	return NULL; /* Ready. Root of trie */
+}
+
+static int fn_trie_flush(struct fib_table *tb)
+{
+	struct trie *t = (struct trie *) tb->tb_data;
+	struct leaf *ll = NULL, *l = NULL;
+	int found = 0, h;
+
+	t->revision++;
+
+	for (h=0; (l = nextleaf(t, l)) != NULL; h++) {
+		found += trie_flush_leaf(t, l);
+
+		if (ll && hlist_empty(&ll->list))
+			trie_leaf_remove(t, ll->key);
+		ll = l;
+	}
+
+	if (ll && hlist_empty(&ll->list))
+		trie_leaf_remove(t, ll->key);
+
+	if(trie_debug) 
+		printk("trie_flush found=%d\n", found);
+	return found;
+}
+
+static int trie_last_dflt=-1;
+
+static void
+fn_trie_select_default(struct fib_table *tb, const struct flowi *flp, struct fib_result *res)
+{
+	struct trie *t = (struct trie *) tb->tb_data;
+	int order, last_idx;
+	struct fib_info *fi = NULL;
+	struct fib_info *last_resort;
+	struct fib_alias *fa = NULL;
+	struct list_head *fa_head;
+	struct leaf *l;
+
+	last_idx = -1;
+	last_resort = NULL;
+	order = -1;
+
+	read_lock(&fib_lock);
+	
+	l = fib_find_node(t, 0);
+	if(!l) 
+		goto out;
+
+	fa_head = get_fa_head(l, 0);
+	if(!fa_head)
+		goto out;
+
+	if (list_empty(fa_head)) 
+		goto out;
+
+	list_for_each_entry(fa, fa_head, fa_list) {
+		struct fib_info *next_fi = fa->fa_info;
+		
+		if (fa->fa_scope != res->scope ||
+		    fa->fa_type != RTN_UNICAST)
+			continue;
+		
+		if (next_fi->fib_priority > res->fi->fib_priority)
+			break;
+		if (!next_fi->fib_nh[0].nh_gw ||
+		    next_fi->fib_nh[0].nh_scope != RT_SCOPE_LINK)
+			continue;
+		fa->fa_state |= FA_S_ACCESSED;
+		
+		if (fi == NULL) {
+			if (next_fi != res->fi)
+				break;
+		} else if (!fib_detect_death(fi, order, &last_resort,
+					     &last_idx, &trie_last_dflt)) {
+			if (res->fi)
+				fib_info_put(res->fi);
+			res->fi = fi;
+			atomic_inc(&fi->fib_clntref);
+			trie_last_dflt = order;
+			goto out;
+		}
+		fi = next_fi;
+		order++;
+	}
+	if (order <= 0 || fi == NULL) {
+		trie_last_dflt = -1;
+		goto out;
+	}
+
+	if (!fib_detect_death(fi, order, &last_resort, &last_idx, &trie_last_dflt)) {
+		if (res->fi)
+			fib_info_put(res->fi);
+		res->fi = fi;
+		atomic_inc(&fi->fib_clntref);
+		trie_last_dflt = order;
+		goto out;
+	}
+	if (last_idx >= 0) {
+		if (res->fi)
+			fib_info_put(res->fi);
+		res->fi = last_resort;
+		if (last_resort)
+			atomic_inc(&last_resort->fib_clntref);
+	}
+	trie_last_dflt = last_idx;
+ out:;
+	read_unlock(&fib_lock);	
+}
+
+static int fn_trie_dump_fa(t_key key, int plen, struct list_head *fah, struct fib_table *tb, 
+			   struct sk_buff *skb, struct netlink_callback *cb)
+{
+	int i, s_i;
+	struct fib_alias *fa;
+
+	u32 xkey=htonl(key);
+
+	s_i=cb->args[3];
+	i = 0;
+
+	list_for_each_entry(fa, fah, fa_list) {
+		if (i < s_i) {
+			i++;
+			continue;
+		}
+		if (fa->fa_info->fib_nh == NULL) {
+			printk("Trie error _fib_nh=NULL in fa[%d] k=%08x plen=%d\n", i, key, plen);
+			i++;
+			continue;
+		}
+		if (fa->fa_info == NULL) {
+			printk("Trie error fa_info=NULL in fa[%d] k=%08x plen=%d\n", i, key, plen);
+			i++;
+			continue;
+		}
+
+		if (fib_dump_info(skb, NETLINK_CB(cb->skb).pid,
+				  cb->nlh->nlmsg_seq,
+				  RTM_NEWROUTE,
+				  tb->tb_id,
+				  fa->fa_type,
+				  fa->fa_scope,
+				  &xkey,
+				  plen,
+				  fa->fa_tos,
+				  fa->fa_info, 0) < 0) {
+			cb->args[3] = i;
+			return -1;
+			}
+		i++;
+	}
+	cb->args[3]=i;
+	return skb->len;
+}
+
+static int fn_trie_dump_plen(struct trie *t, int plen, struct fib_table *tb, struct sk_buff *skb, 
+			     struct netlink_callback *cb)
+{
+	int h, s_h;
+	struct list_head *fa_head;
+	struct leaf *l = NULL;
+	s_h=cb->args[2];
+
+	for (h=0; (l = nextleaf(t, l)) != NULL; h++) {
+
+		if (h < s_h)
+			continue;
+		if (h > s_h)
+			memset(&cb->args[3], 0,
+			       sizeof(cb->args) - 3*sizeof(cb->args[0]));
+
+		fa_head = get_fa_head(l, plen);
+		
+		if(!fa_head)
+			continue;
+
+		if(list_empty(fa_head))
+			continue;
+
+		if (fn_trie_dump_fa(l->key, plen, fa_head, tb, skb, cb)<0) {
+			cb->args[2]=h;
+			return -1;
+		}
+	}
+	cb->args[2]=h;
+	return skb->len;
+}
+
+static int fn_trie_dump(struct fib_table *tb, struct sk_buff *skb, struct netlink_callback *cb)
+{
+	int m, s_m;
+	struct trie *t = (struct trie *) tb->tb_data;
+
+	s_m = cb->args[1];
+
+	read_lock(&fib_lock);
+	for (m=0; m<=32; m++) {
+
+		if (m < s_m)
+			continue;
+		if (m > s_m)
+			memset(&cb->args[2], 0,
+			       sizeof(cb->args) - 2*sizeof(cb->args[0]));
+
+		if (fn_trie_dump_plen(t, 32-m, tb, skb, cb)<0) {
+			cb->args[1] = m;
+			goto out;
+		}
+	}
+	read_unlock(&fib_lock);
+	cb->args[1] = m;
+	return skb->len;
+ out:
+	read_unlock(&fib_lock);
+	return -1;
+}
+
+/* Fix more generic FIB names for init later */
+
+#ifdef CONFIG_IP_MULTIPLE_TABLES
+struct fib_table * fib_hash_init(int id)
+#else
+struct fib_table * __init fib_hash_init(int id)
+#endif
+{
+	struct fib_table *tb;
+	struct trie *t;
+
+	if (fn_alias_kmem == NULL)
+		fn_alias_kmem = kmem_cache_create("ip_fib_alias",
+						  sizeof(struct fib_alias),
+						  0, SLAB_HWCACHE_ALIGN,
+						  NULL, NULL);
+
+	tb = kmalloc(sizeof(struct fib_table) + sizeof(struct trie),
+		     GFP_KERNEL);
+	if (tb == NULL)
+		return NULL;
+
+	tb->tb_id = id;
+	tb->tb_lookup = fn_trie_lookup;
+	tb->tb_insert = fn_trie_insert;
+	tb->tb_delete = fn_trie_delete;
+	tb->tb_flush = fn_trie_flush;
+	tb->tb_select_default = fn_trie_select_default;
+	tb->tb_dump = fn_trie_dump;
+	memset(tb->tb_data, 0, sizeof(struct trie));
+
+	t = (struct trie *) tb->tb_data;
+
+	trie_init(t);
+
+	if (id == RT_TABLE_LOCAL) 
+                trie_local=t;
+	  else if (id == RT_TABLE_MAIN) 
+                trie_main=t;
+
+	if (id == RT_TABLE_LOCAL)
+		printk("IPv4 FIB: Using LC-trie version %s\n", VERSION);
+
+	return tb;
+}
+
+/* Trie dump functions */
+
+static void putspace_seq(struct seq_file *seq, int n)
+{
+	while (n--) seq_printf(seq, " ");
+}
+
+static void printbin_seq(struct seq_file *seq, unsigned int v, int bits)
+{
+	while (bits--)
+		seq_printf(seq, "%s", (v & (1<<bits))?"1":"0");
+}
+
+static void printnode_seq(struct seq_file *seq, int indent, struct node *n, 
+		   int pend, int cindex, int bits)
+{
+	putspace_seq(seq, indent);
+	if (IS_LEAF(n))
+		seq_printf(seq, "|");
+	else
+		seq_printf(seq, "+");
+	if (bits) {
+		seq_printf(seq, "%d/", cindex);
+		printbin_seq(seq, cindex, bits);
+		seq_printf(seq, ": ");
+	}
+	else
+		seq_printf(seq, "<root>: ");
+	seq_printf(seq, "%s:%p ", IS_LEAF(n)?"Leaf":"Internal node", n);
+
+	if (IS_LEAF(n))
+		seq_printf(seq, "key=%d.%d.%d.%d\n", 
+			   n->key >> 24, (n->key >> 16) % 256, (n->key >> 8) % 256, n->key % 256);
+	else {
+		int plen=((struct tnode *)n)->pos;
+		t_key prf=MASK_PFX(n->key, plen);
+		seq_printf(seq, "key=%d.%d.%d.%d/%d\n", 
+			   prf >> 24, (prf >> 16) % 256, (prf >> 8) % 256, prf % 256, plen);
+	}
+	if (IS_LEAF(n)) {
+		struct leaf *l=(struct leaf *)n;
+		struct fib_alias *fa;
+		int i;
+		for (i=32; i>=0; i--)
+		  if(find_leaf_info(&l->list, i)) {
+			
+				struct list_head *fa_head = get_fa_head(l, i);
+				
+				if(!fa_head)
+					continue;
+
+				if(list_empty(fa_head))
+					continue;
+
+				putspace_seq(seq, indent+2);
+				seq_printf(seq, "{/%d...dumping}\n", i);
+
+
+				list_for_each_entry(fa, fa_head, fa_list) {
+					putspace_seq(seq, indent+2);
+					if (fa->fa_info->fib_nh == NULL) {
+						seq_printf(seq, "Error _fib_nh=NULL\n");
+						continue;
+					}
+					if (fa->fa_info == NULL) {
+						seq_printf(seq, "Error fa_info=NULL\n");
+						continue;
+					}
+
+					seq_printf(seq, "{type=%d scope=%d TOS=%d}\n",
+					      fa->fa_type,
+					      fa->fa_scope,
+					      fa->fa_tos);
+				}
+			}
+	}
+	else if (IS_TNODE(n)) {
+		struct tnode *tn=(struct tnode *)n;
+		putspace_seq(seq, indent); seq_printf(seq, "|    ");
+		seq_printf(seq, "{key prefix=%08x/", tn->key&TKEY_GET_MASK(0, tn->pos));
+		printbin_seq(seq, tkey_extract_bits(tn->key, 0, tn->pos), tn->pos);
+		seq_printf(seq, "}\n");
+		putspace_seq(seq, indent); seq_printf(seq, "|    ");
+		seq_printf(seq, "{pos=%d", tn->pos);
+		seq_printf(seq, " (skip=%d bits)", tn->pos - pend);
+		seq_printf(seq, " bits=%d (%u children)}\n", tn->bits, (1 << tn->bits));
+		putspace_seq(seq, indent); seq_printf(seq, "|    ");
+		seq_printf(seq, "{empty=%d full=%d}\n", tn->empty_children, tn->full_children);
+	}
+}
+
+static void trie_dump_seq(struct seq_file *seq, struct trie *t)
+{
+	struct node *n=t->trie;
+	int cindex=0;
+	int indent=1;
+	int pend=0;
+	int depth = 0;
+
+  	read_lock(&fib_lock);
+
+	seq_printf(seq, "------ trie_dump of t=%p ------\n", t);
+	if (n) {
+		printnode_seq(seq, indent, n, pend, cindex, 0);
+		if (IS_TNODE(n)) {
+			struct tnode *tn=(struct tnode *)n;
+			pend = tn->pos+tn->bits;
+			putspace_seq(seq, indent); seq_printf(seq, "\\--\n");
+			indent += 3;
+			depth++;
+
+			while (tn && cindex < (1 << tn->bits)) {
+				if (tn->child[cindex]) {
+					
+					/* Got a child */
+					
+					printnode_seq(seq, indent, tn->child[cindex], pend, cindex, tn->bits);
+					if (IS_LEAF(tn->child[cindex])) { 
+						cindex++;
+						
+					}
+					else {
+						/* 
+						 * New tnode. Decend one level 
+						 */
+						
+						depth++;
+						n=tn->child[cindex];
+						tn=(struct tnode *)n;
+						pend=tn->pos+tn->bits;
+						putspace_seq(seq, indent); seq_printf(seq, "\\--\n");
+						indent+=3;
+						cindex=0;
+					}
+				}
+				else 
+					cindex++;
+
+				/*
+				 * Test if we are done 
+				 */
+				
+				while (cindex >= (1 << tn->bits)) {
+
+					/*
+					 * Move upwards and test for root
+					 * pop off all traversed  nodes
+					 */
+					
+					if (NODE_PARENT(tn) == NULL) {
+						tn = NULL;
+						n = NULL;
+						break;
+					}
+					else {
+						cindex = tkey_extract_bits(tn->key, NODE_PARENT(tn)->pos, NODE_PARENT(tn)->bits);
+						tn = NODE_PARENT(tn);
+						cindex++;
+						n=(struct node *)tn;
+						pend=tn->pos+tn->bits;
+						indent-=3;
+						depth--;
+					}
+				}
+			}
+		}
+		else n = NULL;
+	}
+	else seq_printf(seq, "------ trie is empty\n");
+
+  	read_unlock(&fib_lock);
+}
+
+static struct trie_stat *trie_stat_new(void)
+{
+	struct trie_stat *s = kmalloc(sizeof(struct trie_stat), GFP_KERNEL);
+	int i;
+	
+	if(s) {
+		s->totdepth = 0;
+		s->maxdepth = 0;
+		s->tnodes = 0;
+		s->leaves = 0;
+		s->nullpointers = 0;
+		
+		for(i=0; i< MAX_CHILDS; i++)
+			s->nodesizes[i] = 0;
+	}
+	return s;
+}    
+
+static struct trie_stat *trie_collect_stats(struct trie *t)
+{
+	struct node *n=t->trie;
+	struct trie_stat *s = trie_stat_new();
+	int cindex = 0;
+	int indent = 1;
+	int pend = 0;
+	int depth = 0;
+
+	read_lock(&fib_lock);		
+
+	if (s) {
+		if (n) {
+			if (IS_TNODE(n)) {
+				struct tnode *tn = (struct tnode *)n;
+				pend=tn->pos+tn->bits;
+				indent += 3;
+				s->nodesizes[tn->bits]++;
+				depth++;
+
+				while (tn && cindex < (1 << tn->bits)) {
+					if (tn->child[cindex]) {
+						/* Got a child */
+					
+						if (IS_LEAF(tn->child[cindex])) { 
+							cindex++;
+						
+							/* stats */
+							if (depth > s->maxdepth)
+								s->maxdepth = depth;
+							s->totdepth += depth;
+							s->leaves++;
+						}
+					
+						else {
+							/* 
+							 * New tnode. Decend one level 
+							 */
+						
+							s->tnodes++;
+							s->nodesizes[tn->bits]++;
+							depth++;
+						
+							n = tn->child[cindex];
+							tn = (struct tnode *)n;
+							pend = tn->pos+tn->bits;
+
+							indent += 3;
+							cindex = 0;
+						}
+					}
+					else {
+						cindex++;
+						s->nullpointers++; 
+					}
+
+					/*
+					 * Test if we are done 
+					 */
+				
+					while (cindex >= (1 << tn->bits)) {
+
+						/*
+						 * Move upwards and test for root
+						 * pop off all traversed  nodes
+						 */
+
+						
+						if (NODE_PARENT(tn) == NULL) {
+							tn = NULL;
+							n = NULL;
+							break;
+						}
+						else {
+							cindex = tkey_extract_bits(tn->key, NODE_PARENT(tn)->pos, NODE_PARENT(tn)->bits);
+							tn = NODE_PARENT(tn);
+							cindex++; 
+							n = (struct node *)tn;
+							pend=tn->pos+tn->bits;
+							indent -= 3;
+							depth--;
+						}
+ 					}
+				}
+			}
+			else n = NULL;
+		}
+	}
+
+	read_unlock(&fib_lock);		
+	return s;
+}
+
+#ifdef CONFIG_PROC_FS
+
+static struct fib_alias *fib_triestat_get_first(struct seq_file *seq)
+{
+	return NULL;
+}
+
+static struct fib_alias *fib_triestat_get_next(struct seq_file *seq)
+{
+	return NULL;
+}
+
+static void *fib_triestat_seq_start(struct seq_file *seq, loff_t *pos)
+{
+	void *v = NULL;
+
+	if (ip_fib_main_table)
+		v = *pos ? fib_triestat_get_next(seq) : SEQ_START_TOKEN;
+	return v;
+}
+
+static void *fib_triestat_seq_next(struct seq_file *seq, void *v, loff_t *pos)
+{
+	++*pos;
+	return v == SEQ_START_TOKEN ? fib_triestat_get_first(seq) : fib_triestat_get_next(seq);
+}
+
+static void fib_triestat_seq_stop(struct seq_file *seq, void *v)
+{
+
+}
+
+/* 
+ *	This outputs /proc/net/fib_triestats
+ *
+ *	It always works in backward compatibility mode.
+ *	The format of the file is not supposed to be changed.
+ */
+
+static void collect_and_show(struct trie *t, struct seq_file *seq)
+{
+	int bytes = 0; /* How many bytes are used, a ref is 4 bytes */
+	int i, max, pointers;
+        struct trie_stat *stat;
+	int avdepth;
+
+	stat = trie_collect_stats(t);
+
+	bytes=0;
+	seq_printf(seq, "trie=%p\n", t);
+
+	if (stat) {
+		if (stat->leaves)
+			avdepth=stat->totdepth*100 / stat->leaves;
+		else
+			avdepth=0;
+		seq_printf(seq, "Aver depth: %d.%02d\n", avdepth / 100, avdepth % 100 );
+		seq_printf(seq, "Max depth: %4d\n", stat->maxdepth);
+				
+		seq_printf(seq, "Leaves: %d\n", stat->leaves);
+		bytes += sizeof(struct leaf) * stat->leaves;
+		seq_printf(seq, "Internal nodes: %d\n", stat->tnodes);
+		bytes += sizeof(struct tnode) * stat->tnodes;
+
+		max = MAX_CHILDS-1;
+
+		while (max >= 0 && stat->nodesizes[max] == 0)
+			max--;
+		pointers = 0;
+
+		for (i = 1; i <= max; i++) 
+			if (stat->nodesizes[i] != 0) {
+				seq_printf(seq, "  %d: %d",  i, stat->nodesizes[i]);
+				pointers += (1<<i) * stat->nodesizes[i];
+			}
+		seq_printf(seq, "\n");
+		seq_printf(seq, "Pointers: %d\n", pointers);
+		bytes += sizeof(struct node *) * pointers;
+		seq_printf(seq, "Null ptrs: %d\n", stat->nullpointers);
+		seq_printf(seq, "Total size: %d  kB\n", bytes / 1024);
+
+		kfree(stat);
+	}
+
+#ifdef CONFIG_IP_FIB_TRIE_STATS
+	seq_printf(seq, "Counters:\n---------\n");
+	seq_printf(seq,"gets = %d\n", t->stats.gets);
+	seq_printf(seq,"backtracks = %d\n", t->stats.backtrack);
+	seq_printf(seq,"semantic match passed = %d\n", t->stats.semantic_match_passed);
+	seq_printf(seq,"semantic match miss = %d\n", t->stats.semantic_match_miss);
+	seq_printf(seq,"null node hit= %d\n", t->stats.null_node_hit);
+#ifdef CLEAR_STATS
+	memset(&(t->stats), 0, sizeof(t->stats));
+#endif
+#endif /*  CONFIG_IP_FIB_TRIE_STATS */
+}
+
+static int fib_triestat_seq_show(struct seq_file *seq, void *v)
+{
+	char bf[128];
+    
+	if (v == SEQ_START_TOKEN) {
+		seq_printf(seq, "Basic info: size of leaf: %Zd bytes, size of tnode: %Zd bytes.\n", 
+			   sizeof(struct leaf), sizeof(struct tnode));
+		if (trie_local) 
+			collect_and_show(trie_local, seq);
+
+		if (trie_main) 
+			collect_and_show(trie_main, seq);
+	}
+	else {
+		snprintf(bf, sizeof(bf),
+			 "*\t%08X\t%08X", 200, 400);
+		
+		seq_printf(seq, "%-127s\n", bf);
+	}
+	return 0;
+}
+
+static struct seq_operations fib_triestat_seq_ops = {
+	.start  = fib_triestat_seq_start,
+	.next   = fib_triestat_seq_next,
+	.stop   = fib_triestat_seq_stop,
+	.show   = fib_triestat_seq_show,
+};
+
+static int fib_triestat_seq_open(struct inode *inode, struct file *file)
+{
+	struct seq_file *seq;
+	int rc = -ENOMEM;
+
+	rc = seq_open(file, &fib_triestat_seq_ops);
+	if (rc)
+		goto out_kfree;
+
+	seq	     = file->private_data;
+out:
+	return rc;
+out_kfree:
+	goto out;
+}
+
+static struct file_operations fib_triestat_seq_fops = {
+	.owner		= THIS_MODULE,
+	.open           = fib_triestat_seq_open,
+	.read           = seq_read,
+	.llseek         = seq_lseek,
+	.release	= seq_release_private,
+};
+
+int __init fib_stat_proc_init(void)
+{
+	if (!proc_net_fops_create("fib_triestat", S_IRUGO, &fib_triestat_seq_fops))
+		return -ENOMEM;
+	return 0;
+}
+
+void __init fib_stat_proc_exit(void)
+{
+	proc_net_remove("fib_triestat");
+}
+
+static struct fib_alias *fib_trie_get_first(struct seq_file *seq)
+{
+	return NULL;
+}
+
+static struct fib_alias *fib_trie_get_next(struct seq_file *seq)
+{
+	return NULL;
+}
+
+static void *fib_trie_seq_start(struct seq_file *seq, loff_t *pos)
+{
+	void *v = NULL;
+
+	if (ip_fib_main_table)
+		v = *pos ? fib_trie_get_next(seq) : SEQ_START_TOKEN;
+	return v;
+}
+
+static void *fib_trie_seq_next(struct seq_file *seq, void *v, loff_t *pos)
+{
+	++*pos;
+	return v == SEQ_START_TOKEN ? fib_trie_get_first(seq) : fib_trie_get_next(seq);
+}
+
+static void fib_trie_seq_stop(struct seq_file *seq, void *v)
+{
+
+}
+
+/* 
+ *	This outputs /proc/net/fib_trie.
+ *
+ *	It always works in backward compatibility mode.
+ *	The format of the file is not supposed to be changed.
+ */
+
+static int fib_trie_seq_show(struct seq_file *seq, void *v)
+{
+	char bf[128];
+
+	if (v == SEQ_START_TOKEN) {
+		if (trie_local) 
+			trie_dump_seq(seq, trie_local);
+
+		if (trie_main) 
+			trie_dump_seq(seq, trie_main);
+	}
+
+	else {
+		snprintf(bf, sizeof(bf),
+			 "*\t%08X\t%08X", 200, 400);
+		seq_printf(seq, "%-127s\n", bf);
+	}
+
+	return 0;
+}
+
+static struct seq_operations fib_trie_seq_ops = {
+	.start  = fib_trie_seq_start,
+	.next   = fib_trie_seq_next,
+	.stop   = fib_trie_seq_stop,
+	.show   = fib_trie_seq_show,
+};
+
+static int fib_trie_seq_open(struct inode *inode, struct file *file)
+{
+	struct seq_file *seq;
+	int rc = -ENOMEM;
+
+	rc = seq_open(file, &fib_trie_seq_ops);
+	if (rc)
+		goto out_kfree;
+
+	seq	     = file->private_data;
+out:
+	return rc;
+out_kfree:
+	goto out;
+}
+
+static struct file_operations fib_trie_seq_fops = {
+	.owner		= THIS_MODULE,
+	.open           = fib_trie_seq_open,
+	.read           = seq_read,
+	.llseek         = seq_lseek,
+	.release	= seq_release_private,
+};
+
+int __init fib_proc_init(void)
+{
+	if (!proc_net_fops_create("fib_trie", S_IRUGO, &fib_trie_seq_fops))
+		return -ENOMEM;
+	return 0;
+}
+
+void __init fib_proc_exit(void)
+{
+	proc_net_remove("fib_trie");
+}
+
+#endif /* CONFIG_PROC_FS */
diff --git a/net/ipv4/ip_input.c b/net/ipv4/ip_input.c
index 4e47a26..af2ec88 100644
--- a/net/ipv4/ip_input.c
+++ b/net/ipv4/ip_input.c
@@ -184,6 +184,7 @@
 					raw_rcv(last, skb2);
 			}
 			last = sk;
+			nf_reset(skb);
 		}
 	}
 
@@ -200,10 +201,6 @@
 {
 	int ihl = skb->nh.iph->ihl*4;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	nf_debug_ip_local_deliver(skb);
-#endif /*CONFIG_NETFILTER_DEBUG*/
-
 	__skb_pull(skb, ihl);
 
 	/* Free reference early: we don't need it any more, and it may
diff --git a/net/ipv4/ip_output.c b/net/ipv4/ip_output.c
index 760dc82..ee07aec 100644
--- a/net/ipv4/ip_output.c
+++ b/net/ipv4/ip_output.c
@@ -107,10 +107,6 @@
 	newskb->pkt_type = PACKET_LOOPBACK;
 	newskb->ip_summed = CHECKSUM_UNNECESSARY;
 	BUG_TRAP(newskb->dst);
-
-#ifdef CONFIG_NETFILTER_DEBUG
-	nf_debug_ip_loopback_xmit(newskb);
-#endif
 	nf_reset(newskb);
 	netif_rx(newskb);
 	return 0;
@@ -192,10 +188,6 @@
 		skb = skb2;
 	}
 
-#ifdef CONFIG_NETFILTER_DEBUG
-	nf_debug_ip_finish_output2(skb);
-#endif /*CONFIG_NETFILTER_DEBUG*/
-
 	nf_reset(skb);
 
 	if (hh) {
@@ -415,9 +407,6 @@
 	to->nf_bridge = from->nf_bridge;
 	nf_bridge_get(to->nf_bridge);
 #endif
-#ifdef CONFIG_NETFILTER_DEBUG
-	to->nf_debug = from->nf_debug;
-#endif
 #endif
 }
 
diff --git a/net/ipv4/ipmr.c b/net/ipv4/ipmr.c
index e21c049..e4f809a 100644
--- a/net/ipv4/ipmr.c
+++ b/net/ipv4/ipmr.c
@@ -1350,6 +1350,7 @@
 			     */
 			    read_lock(&mrt_lock);
 			    if (mroute_socket) {
+				    nf_reset(skb);
 				    raw_rcv(mroute_socket, skb);
 				    read_unlock(&mrt_lock);
 				    return 0;
diff --git a/net/ipv4/ipvs/ip_vs_xmit.c b/net/ipv4/ipvs/ip_vs_xmit.c
index de21da0..a8512a3 100644
--- a/net/ipv4/ipvs/ip_vs_xmit.c
+++ b/net/ipv4/ipvs/ip_vs_xmit.c
@@ -127,7 +127,6 @@
 
 #define IP_VS_XMIT(skb, rt)				\
 do {							\
-	nf_reset_debug(skb);				\
 	(skb)->nfcache |= NFC_IPVS_PROPERTY;		\
 	(skb)->ip_summed = CHECKSUM_NONE;		\
 	NF_HOOK(PF_INET, NF_IP_LOCAL_OUT, (skb), NULL,	\
diff --git a/net/ipv4/netfilter/arp_tables.c b/net/ipv4/netfilter/arp_tables.c
index df79f5e..fa16342 100644
--- a/net/ipv4/netfilter/arp_tables.c
+++ b/net/ipv4/netfilter/arp_tables.c
@@ -60,7 +60,6 @@
 
 #define ASSERT_READ_LOCK(x) ARP_NF_ASSERT(down_trylock(&arpt_mutex) != 0)
 #define ASSERT_WRITE_LOCK(x) ARP_NF_ASSERT(down_trylock(&arpt_mutex) != 0)
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <linux/netfilter_ipv4/listhelp.h>
 
 struct arpt_table_info {
diff --git a/net/ipv4/netfilter/ip_conntrack_amanda.c b/net/ipv4/netfilter/ip_conntrack_amanda.c
index 3dbddd0..a78a320 100644
--- a/net/ipv4/netfilter/ip_conntrack_amanda.c
+++ b/net/ipv4/netfilter/ip_conntrack_amanda.c
@@ -26,7 +26,6 @@
 #include <net/checksum.h>
 #include <net/udp.h>
 
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <linux/netfilter_ipv4/ip_conntrack_helper.h>
 #include <linux/netfilter_ipv4/ip_conntrack_amanda.h>
 
@@ -42,7 +41,7 @@
 
 /* This is slow, but it's simple. --RR */
 static char amanda_buffer[65536];
-static DECLARE_LOCK(amanda_buffer_lock);
+static DEFINE_SPINLOCK(amanda_buffer_lock);
 
 unsigned int (*ip_nat_amanda_hook)(struct sk_buff **pskb,
 				   enum ip_conntrack_info ctinfo,
@@ -76,7 +75,7 @@
 		return NF_ACCEPT;
 	}
 
-	LOCK_BH(&amanda_buffer_lock);
+	spin_lock_bh(&amanda_buffer_lock);
 	skb_copy_bits(*pskb, dataoff, amanda_buffer, (*pskb)->len - dataoff);
 	data = amanda_buffer;
 	data_limit = amanda_buffer + (*pskb)->len - dataoff;
@@ -134,7 +133,7 @@
 	}
 
 out:
-	UNLOCK_BH(&amanda_buffer_lock);
+	spin_unlock_bh(&amanda_buffer_lock);
 	return ret;
 }
 
diff --git a/net/ipv4/netfilter/ip_conntrack_core.c b/net/ipv4/netfilter/ip_conntrack_core.c
index 09e8246..4b78ebe 100644
--- a/net/ipv4/netfilter/ip_conntrack_core.c
+++ b/net/ipv4/netfilter/ip_conntrack_core.c
@@ -38,10 +38,10 @@
 #include <linux/percpu.h>
 #include <linux/moduleparam.h>
 
-/* This rwlock protects the main hash table, protocol/helper/expected
+/* ip_conntrack_lock protects the main hash table, protocol/helper/expected
    registrations, conntrack timers*/
-#define ASSERT_READ_LOCK(x) MUST_BE_READ_LOCKED(&ip_conntrack_lock)
-#define ASSERT_WRITE_LOCK(x) MUST_BE_WRITE_LOCKED(&ip_conntrack_lock)
+#define ASSERT_READ_LOCK(x)
+#define ASSERT_WRITE_LOCK(x)
 
 #include <linux/netfilter_ipv4/ip_conntrack.h>
 #include <linux/netfilter_ipv4/ip_conntrack_protocol.h>
@@ -57,7 +57,7 @@
 #define DEBUGP(format, args...)
 #endif
 
-DECLARE_RWLOCK(ip_conntrack_lock);
+DEFINE_RWLOCK(ip_conntrack_lock);
 
 /* ip_conntrack_standalone needs this */
 atomic_t ip_conntrack_count = ATOMIC_INIT(0);
@@ -147,7 +147,7 @@
 
 static void unlink_expect(struct ip_conntrack_expect *exp)
 {
-	MUST_BE_WRITE_LOCKED(&ip_conntrack_lock);
+	ASSERT_WRITE_LOCK(&ip_conntrack_lock);
 	list_del(&exp->list);
 	/* Logically in destroy_expect, but we hold the lock here. */
 	exp->master->expecting--;
@@ -157,9 +157,9 @@
 {
 	struct ip_conntrack_expect *exp = (void *)ul_expect;
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	unlink_expect(exp);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 	destroy_expect(exp);
 }
 
@@ -209,7 +209,7 @@
 	unsigned int ho, hr;
 	
 	DEBUGP("clean_from_lists(%p)\n", ct);
-	MUST_BE_WRITE_LOCKED(&ip_conntrack_lock);
+	ASSERT_WRITE_LOCK(&ip_conntrack_lock);
 
 	ho = hash_conntrack(&ct->tuplehash[IP_CT_DIR_ORIGINAL].tuple);
 	hr = hash_conntrack(&ct->tuplehash[IP_CT_DIR_REPLY].tuple);
@@ -240,7 +240,7 @@
 	if (ip_conntrack_destroyed)
 		ip_conntrack_destroyed(ct);
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	/* Expectations will have been removed in clean_from_lists,
 	 * except TFTP can create an expectation on the first packet,
 	 * before connection is in the list, so we need to clean here,
@@ -254,7 +254,7 @@
 	}
 
 	CONNTRACK_STAT_INC(delete);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	if (ct->master)
 		ip_conntrack_put(ct->master);
@@ -268,12 +268,12 @@
 {
 	struct ip_conntrack *ct = (void *)ul_conntrack;
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	/* Inside lock so preempt is disabled on module removal path.
 	 * Otherwise we can get spurious warnings. */
 	CONNTRACK_STAT_INC(delete_list);
 	clean_from_lists(ct);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 	ip_conntrack_put(ct);
 }
 
@@ -282,7 +282,7 @@
 		    const struct ip_conntrack_tuple *tuple,
 		    const struct ip_conntrack *ignored_conntrack)
 {
-	MUST_BE_READ_LOCKED(&ip_conntrack_lock);
+	ASSERT_READ_LOCK(&ip_conntrack_lock);
 	return tuplehash_to_ctrack(i) != ignored_conntrack
 		&& ip_ct_tuple_equal(tuple, &i->tuple);
 }
@@ -294,7 +294,7 @@
 	struct ip_conntrack_tuple_hash *h;
 	unsigned int hash = hash_conntrack(tuple);
 
-	MUST_BE_READ_LOCKED(&ip_conntrack_lock);
+	ASSERT_READ_LOCK(&ip_conntrack_lock);
 	list_for_each_entry(h, &ip_conntrack_hash[hash], list) {
 		if (conntrack_tuple_cmp(h, tuple, ignored_conntrack)) {
 			CONNTRACK_STAT_INC(found);
@@ -313,11 +313,11 @@
 {
 	struct ip_conntrack_tuple_hash *h;
 
-	READ_LOCK(&ip_conntrack_lock);
+	read_lock_bh(&ip_conntrack_lock);
 	h = __ip_conntrack_find(tuple, ignored_conntrack);
 	if (h)
 		atomic_inc(&tuplehash_to_ctrack(h)->ct_general.use);
-	READ_UNLOCK(&ip_conntrack_lock);
+	read_unlock_bh(&ip_conntrack_lock);
 
 	return h;
 }
@@ -352,7 +352,7 @@
 	IP_NF_ASSERT(!is_confirmed(ct));
 	DEBUGP("Confirming conntrack %p\n", ct);
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 
 	/* See if there's one in the list already, including reverse:
            NAT could have grabbed it without realizing, since we're
@@ -380,12 +380,12 @@
 		atomic_inc(&ct->ct_general.use);
 		set_bit(IPS_CONFIRMED_BIT, &ct->status);
 		CONNTRACK_STAT_INC(insert);
-		WRITE_UNLOCK(&ip_conntrack_lock);
+		write_unlock_bh(&ip_conntrack_lock);
 		return NF_ACCEPT;
 	}
 
 	CONNTRACK_STAT_INC(insert_failed);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	return NF_DROP;
 }
@@ -398,9 +398,9 @@
 {
 	struct ip_conntrack_tuple_hash *h;
 
-	READ_LOCK(&ip_conntrack_lock);
+	read_lock_bh(&ip_conntrack_lock);
 	h = __ip_conntrack_find(tuple, ignored_conntrack);
-	READ_UNLOCK(&ip_conntrack_lock);
+	read_unlock_bh(&ip_conntrack_lock);
 
 	return h != NULL;
 }
@@ -419,13 +419,13 @@
 	struct ip_conntrack *ct = NULL;
 	int dropped = 0;
 
-	READ_LOCK(&ip_conntrack_lock);
+	read_lock_bh(&ip_conntrack_lock);
 	h = LIST_FIND_B(chain, unreplied, struct ip_conntrack_tuple_hash *);
 	if (h) {
 		ct = tuplehash_to_ctrack(h);
 		atomic_inc(&ct->ct_general.use);
 	}
-	READ_UNLOCK(&ip_conntrack_lock);
+	read_unlock_bh(&ip_conntrack_lock);
 
 	if (!ct)
 		return dropped;
@@ -508,7 +508,7 @@
 	conntrack->timeout.data = (unsigned long)conntrack;
 	conntrack->timeout.function = death_by_timeout;
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	exp = find_expectation(tuple);
 
 	if (exp) {
@@ -532,7 +532,7 @@
 	list_add(&conntrack->tuplehash[IP_CT_DIR_ORIGINAL].list, &unconfirmed);
 
 	atomic_inc(&ip_conntrack_count);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	if (exp) {
 		if (exp->expectfn)
@@ -723,17 +723,17 @@
 {
 	struct ip_conntrack_expect *i;
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	/* choose the the oldest expectation to evict */
 	list_for_each_entry_reverse(i, &ip_conntrack_expect_list, list) {
 		if (expect_matches(i, exp) && del_timer(&i->timeout)) {
 			unlink_expect(i);
-			WRITE_UNLOCK(&ip_conntrack_lock);
+			write_unlock_bh(&ip_conntrack_lock);
 			destroy_expect(i);
 			return;
 		}
 	}
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 }
 
 struct ip_conntrack_expect *ip_conntrack_expect_alloc(void)
@@ -760,15 +760,11 @@
 	exp->master->expecting++;
 	list_add(&exp->list, &ip_conntrack_expect_list);
 
-	if (exp->master->helper->timeout) {
-		init_timer(&exp->timeout);
-		exp->timeout.data = (unsigned long)exp;
-		exp->timeout.function = expectation_timed_out;
-		exp->timeout.expires
-			= jiffies + exp->master->helper->timeout * HZ;
-		add_timer(&exp->timeout);
-	} else
-		exp->timeout.function = NULL;
+	init_timer(&exp->timeout);
+	exp->timeout.data = (unsigned long)exp;
+	exp->timeout.function = expectation_timed_out;
+	exp->timeout.expires = jiffies + exp->master->helper->timeout * HZ;
+	add_timer(&exp->timeout);
 
 	CONNTRACK_STAT_INC(expect_create);
 }
@@ -808,7 +804,7 @@
 	DEBUGP("tuple: "); DUMP_TUPLE(&expect->tuple);
 	DEBUGP("mask:  "); DUMP_TUPLE(&expect->mask);
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	list_for_each_entry(i, &ip_conntrack_expect_list, list) {
 		if (expect_matches(i, expect)) {
 			/* Refresh timer: if it's dying, ignore.. */
@@ -832,7 +828,7 @@
 	ip_conntrack_expect_insert(expect);
 	ret = 0;
 out:
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
  	return ret;
 }
 
@@ -841,7 +837,7 @@
 void ip_conntrack_alter_reply(struct ip_conntrack *conntrack,
 			      const struct ip_conntrack_tuple *newreply)
 {
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	/* Should be unconfirmed, so not in hash table yet */
 	IP_NF_ASSERT(!is_confirmed(conntrack));
 
@@ -851,15 +847,15 @@
 	conntrack->tuplehash[IP_CT_DIR_REPLY].tuple = *newreply;
 	if (!conntrack->master && conntrack->expecting == 0)
 		conntrack->helper = ip_ct_find_helper(newreply);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 }
 
 int ip_conntrack_helper_register(struct ip_conntrack_helper *me)
 {
 	BUG_ON(me->timeout == 0);
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	list_prepend(&helpers, me);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	return 0;
 }
@@ -878,7 +874,7 @@
 	struct ip_conntrack_expect *exp, *tmp;
 
 	/* Need write lock here, to delete helper. */
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	LIST_DELETE(&helpers, me);
 
 	/* Get rid of expectations */
@@ -893,7 +889,7 @@
 	for (i = 0; i < ip_conntrack_htable_size; i++)
 		LIST_FIND_W(&ip_conntrack_hash[i], unhelp,
 			    struct ip_conntrack_tuple_hash *, me);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	/* Someone could be still looking at the helper in a bh. */
 	synchronize_net();
@@ -925,14 +921,14 @@
 		ct->timeout.expires = extra_jiffies;
 		ct_add_counters(ct, ctinfo, skb);
 	} else {
-		WRITE_LOCK(&ip_conntrack_lock);
+		write_lock_bh(&ip_conntrack_lock);
 		/* Need del_timer for race avoidance (may already be dying). */
 		if (del_timer(&ct->timeout)) {
 			ct->timeout.expires = jiffies + extra_jiffies;
 			add_timer(&ct->timeout);
 		}
 		ct_add_counters(ct, ctinfo, skb);
-		WRITE_UNLOCK(&ip_conntrack_lock);
+		write_unlock_bh(&ip_conntrack_lock);
 	}
 }
 
@@ -940,10 +936,6 @@
 struct sk_buff *
 ip_ct_gather_frags(struct sk_buff *skb, u_int32_t user)
 {
-#ifdef CONFIG_NETFILTER_DEBUG
-	unsigned int olddebug = skb->nf_debug;
-#endif
-
 	skb_orphan(skb);
 
 	local_bh_disable(); 
@@ -953,12 +945,7 @@
 	if (skb) {
 		ip_send_check(skb->nh.iph);
 		skb->nfcache |= NFC_ALTERED;
-#ifdef CONFIG_NETFILTER_DEBUG
-		/* Packet path as if nothing had happened. */
-		skb->nf_debug = olddebug;
-#endif
 	}
-
 	return skb;
 }
 
@@ -997,7 +984,7 @@
 {
 	struct ip_conntrack_tuple_hash *h = NULL;
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	for (; *bucket < ip_conntrack_htable_size; (*bucket)++) {
 		h = LIST_FIND_W(&ip_conntrack_hash[*bucket], do_iter,
 				struct ip_conntrack_tuple_hash *, iter, data);
@@ -1009,7 +996,7 @@
 				struct ip_conntrack_tuple_hash *, iter, data);
 	if (h)
 		atomic_inc(&tuplehash_to_ctrack(h)->ct_general.use);
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	return h;
 }
@@ -1201,14 +1188,14 @@
 	}
 
 	/* Don't NEED lock here, but good form anyway. */
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	for (i = 0; i < MAX_IP_CT_PROTO; i++)
 		ip_ct_protos[i] = &ip_conntrack_generic_protocol;
 	/* Sew in builtin protocols. */
 	ip_ct_protos[IPPROTO_TCP] = &ip_conntrack_protocol_tcp;
 	ip_ct_protos[IPPROTO_UDP] = &ip_conntrack_protocol_udp;
 	ip_ct_protos[IPPROTO_ICMP] = &ip_conntrack_protocol_icmp;
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 
 	for (i = 0; i < ip_conntrack_htable_size; i++)
 		INIT_LIST_HEAD(&ip_conntrack_hash[i]);
diff --git a/net/ipv4/netfilter/ip_conntrack_ftp.c b/net/ipv4/netfilter/ip_conntrack_ftp.c
index dd86503..fea6dd2 100644
--- a/net/ipv4/netfilter/ip_conntrack_ftp.c
+++ b/net/ipv4/netfilter/ip_conntrack_ftp.c
@@ -16,7 +16,6 @@
 #include <net/checksum.h>
 #include <net/tcp.h>
 
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <linux/netfilter_ipv4/ip_conntrack_helper.h>
 #include <linux/netfilter_ipv4/ip_conntrack_ftp.h>
 #include <linux/moduleparam.h>
@@ -28,7 +27,7 @@
 /* This is slow, but it's simple. --RR */
 static char ftp_buffer[65536];
 
-static DECLARE_LOCK(ip_ftp_lock);
+static DEFINE_SPINLOCK(ip_ftp_lock);
 
 #define MAX_PORTS 8
 static int ports[MAX_PORTS];
@@ -319,7 +318,7 @@
 	}
 	datalen = (*pskb)->len - dataoff;
 
-	LOCK_BH(&ip_ftp_lock);
+	spin_lock_bh(&ip_ftp_lock);
 	fb_ptr = skb_header_pointer(*pskb, dataoff,
 				    (*pskb)->len - dataoff, ftp_buffer);
 	BUG_ON(fb_ptr == NULL);
@@ -442,7 +441,7 @@
 	if (ends_in_nl)
 		update_nl_seq(seq, ct_ftp_info,dir);
  out:
-	UNLOCK_BH(&ip_ftp_lock);
+	spin_unlock_bh(&ip_ftp_lock);
 	return ret;
 }
 
diff --git a/net/ipv4/netfilter/ip_conntrack_irc.c b/net/ipv4/netfilter/ip_conntrack_irc.c
index 33cc734..cd98772 100644
--- a/net/ipv4/netfilter/ip_conntrack_irc.c
+++ b/net/ipv4/netfilter/ip_conntrack_irc.c
@@ -29,7 +29,6 @@
 #include <net/checksum.h>
 #include <net/tcp.h>
 
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <linux/netfilter_ipv4/ip_conntrack_helper.h>
 #include <linux/netfilter_ipv4/ip_conntrack_irc.h>
 #include <linux/moduleparam.h>
@@ -41,7 +40,7 @@
 static unsigned int dcc_timeout = 300;
 /* This is slow, but it's simple. --RR */
 static char irc_buffer[65536];
-static DECLARE_LOCK(irc_buffer_lock);
+static DEFINE_SPINLOCK(irc_buffer_lock);
 
 unsigned int (*ip_nat_irc_hook)(struct sk_buff **pskb,
 				enum ip_conntrack_info ctinfo,
@@ -141,7 +140,7 @@
 	if (dataoff >= (*pskb)->len)
 		return NF_ACCEPT;
 
-	LOCK_BH(&irc_buffer_lock);
+	spin_lock_bh(&irc_buffer_lock);
 	ib_ptr = skb_header_pointer(*pskb, dataoff,
 				    (*pskb)->len - dataoff, irc_buffer);
 	BUG_ON(ib_ptr == NULL);
@@ -237,7 +236,7 @@
 	} /* while data < ... */
 
  out:
-	UNLOCK_BH(&irc_buffer_lock);
+	spin_unlock_bh(&irc_buffer_lock);
 	return ret;
 }
 
diff --git a/net/ipv4/netfilter/ip_conntrack_proto_sctp.c b/net/ipv4/netfilter/ip_conntrack_proto_sctp.c
index ff8c34a..31d7539 100644
--- a/net/ipv4/netfilter/ip_conntrack_proto_sctp.c
+++ b/net/ipv4/netfilter/ip_conntrack_proto_sctp.c
@@ -26,7 +26,6 @@
 
 #include <linux/netfilter_ipv4/ip_conntrack.h>
 #include <linux/netfilter_ipv4/ip_conntrack_protocol.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 #if 0
 #define DEBUGP(format, ...) printk(format, ## __VA_ARGS__)
@@ -35,7 +34,7 @@
 #endif
 
 /* Protects conntrack->proto.sctp */
-static DECLARE_RWLOCK(sctp_lock);
+static DEFINE_RWLOCK(sctp_lock);
 
 /* FIXME: Examine ipfilter's timeouts and conntrack transitions more
    closely.  They're more complex. --RR 
@@ -199,9 +198,9 @@
 	DEBUGP(__FUNCTION__);
 	DEBUGP("\n");
 
-	READ_LOCK(&sctp_lock);
+	read_lock_bh(&sctp_lock);
 	state = conntrack->proto.sctp.state;
-	READ_UNLOCK(&sctp_lock);
+	read_unlock_bh(&sctp_lock);
 
 	return seq_printf(s, "%s ", sctp_conntrack_names[state]);
 }
@@ -343,13 +342,13 @@
 
 	oldsctpstate = newconntrack = SCTP_CONNTRACK_MAX;
 	for_each_sctp_chunk (skb, sch, _sch, offset, count) {
-		WRITE_LOCK(&sctp_lock);
+		write_lock_bh(&sctp_lock);
 
 		/* Special cases of Verification tag check (Sec 8.5.1) */
 		if (sch->type == SCTP_CID_INIT) {
 			/* Sec 8.5.1 (A) */
 			if (sh->vtag != 0) {
-				WRITE_UNLOCK(&sctp_lock);
+				write_unlock_bh(&sctp_lock);
 				return -1;
 			}
 		} else if (sch->type == SCTP_CID_ABORT) {
@@ -357,7 +356,7 @@
 			if (!(sh->vtag == conntrack->proto.sctp.vtag[CTINFO2DIR(ctinfo)])
 				&& !(sh->vtag == conntrack->proto.sctp.vtag
 							[1 - CTINFO2DIR(ctinfo)])) {
-				WRITE_UNLOCK(&sctp_lock);
+				write_unlock_bh(&sctp_lock);
 				return -1;
 			}
 		} else if (sch->type == SCTP_CID_SHUTDOWN_COMPLETE) {
@@ -366,13 +365,13 @@
 				&& !(sh->vtag == conntrack->proto.sctp.vtag
 							[1 - CTINFO2DIR(ctinfo)] 
 					&& (sch->flags & 1))) {
-				WRITE_UNLOCK(&sctp_lock);
+				write_unlock_bh(&sctp_lock);
 				return -1;
 			}
 		} else if (sch->type == SCTP_CID_COOKIE_ECHO) {
 			/* Sec 8.5.1 (D) */
 			if (!(sh->vtag == conntrack->proto.sctp.vtag[CTINFO2DIR(ctinfo)])) {
-				WRITE_UNLOCK(&sctp_lock);
+				write_unlock_bh(&sctp_lock);
 				return -1;
 			}
 		}
@@ -384,7 +383,7 @@
 		if (newconntrack == SCTP_CONNTRACK_MAX) {
 			DEBUGP("ip_conntrack_sctp: Invalid dir=%i ctype=%u conntrack=%u\n",
 			       CTINFO2DIR(ctinfo), sch->type, oldsctpstate);
-			WRITE_UNLOCK(&sctp_lock);
+			write_unlock_bh(&sctp_lock);
 			return -1;
 		}
 
@@ -396,7 +395,7 @@
 			ih = skb_header_pointer(skb, offset + sizeof(sctp_chunkhdr_t),
 			                        sizeof(_inithdr), &_inithdr);
 			if (ih == NULL) {
-					WRITE_UNLOCK(&sctp_lock);
+					write_unlock_bh(&sctp_lock);
 					return -1;
 			}
 			DEBUGP("Setting vtag %x for dir %d\n", 
@@ -405,7 +404,7 @@
 		}
 
 		conntrack->proto.sctp.state = newconntrack;
-		WRITE_UNLOCK(&sctp_lock);
+		write_unlock_bh(&sctp_lock);
 	}
 
 	ip_ct_refresh_acct(conntrack, ctinfo, skb, *sctp_timeouts[newconntrack]);
diff --git a/net/ipv4/netfilter/ip_conntrack_proto_tcp.c b/net/ipv4/netfilter/ip_conntrack_proto_tcp.c
index 721ddbf..809dfed 100644
--- a/net/ipv4/netfilter/ip_conntrack_proto_tcp.c
+++ b/net/ipv4/netfilter/ip_conntrack_proto_tcp.c
@@ -36,7 +36,6 @@
 #include <linux/netfilter_ipv4.h>
 #include <linux/netfilter_ipv4/ip_conntrack.h>
 #include <linux/netfilter_ipv4/ip_conntrack_protocol.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 #if 0
 #define DEBUGP printk
@@ -46,7 +45,7 @@
 #endif
 
 /* Protects conntrack->proto.tcp */
-static DECLARE_RWLOCK(tcp_lock);
+static DEFINE_RWLOCK(tcp_lock);
 
 /* "Be conservative in what you do, 
     be liberal in what you accept from others." 
@@ -330,9 +329,9 @@
 {
 	enum tcp_conntrack state;
 
-	READ_LOCK(&tcp_lock);
+	read_lock_bh(&tcp_lock);
 	state = conntrack->proto.tcp.state;
-	READ_UNLOCK(&tcp_lock);
+	read_unlock_bh(&tcp_lock);
 
 	return seq_printf(s, "%s ", tcp_conntrack_names[state]);
 }
@@ -738,14 +737,14 @@
 
 	end = segment_seq_plus_len(ntohl(tcph->seq), skb->len, iph, tcph);
 	
-	WRITE_LOCK(&tcp_lock);
+	write_lock_bh(&tcp_lock);
 	/*
 	 * We have to worry for the ack in the reply packet only...
 	 */
 	if (after(end, conntrack->proto.tcp.seen[dir].td_end))
 		conntrack->proto.tcp.seen[dir].td_end = end;
 	conntrack->proto.tcp.last_end = end;
-	WRITE_UNLOCK(&tcp_lock);
+	write_unlock_bh(&tcp_lock);
 	DEBUGP("tcp_update: sender end=%u maxend=%u maxwin=%u scale=%i "
 	       "receiver end=%u maxend=%u maxwin=%u scale=%i\n",
 		sender->td_end, sender->td_maxend, sender->td_maxwin,
@@ -857,7 +856,7 @@
 				sizeof(_tcph), &_tcph);
 	BUG_ON(th == NULL);
 	
-	WRITE_LOCK(&tcp_lock);
+	write_lock_bh(&tcp_lock);
 	old_state = conntrack->proto.tcp.state;
 	dir = CTINFO2DIR(ctinfo);
 	index = get_conntrack_index(th);
@@ -879,7 +878,7 @@
 			 * that the client cannot but retransmit its SYN and 
 			 * thus initiate a clean new session.
 			 */
-		    	WRITE_UNLOCK(&tcp_lock);
+		    	write_unlock_bh(&tcp_lock);
 			if (LOG_INVALID(IPPROTO_TCP))
 				nf_log_packet(PF_INET, 0, skb, NULL, NULL, 
 					  "ip_ct_tcp: killing out of sync session ");
@@ -894,7 +893,7 @@
 		conntrack->proto.tcp.last_end = 
 		    segment_seq_plus_len(ntohl(th->seq), skb->len, iph, th);
 		
-		WRITE_UNLOCK(&tcp_lock);
+		write_unlock_bh(&tcp_lock);
 		if (LOG_INVALID(IPPROTO_TCP))
 			nf_log_packet(PF_INET, 0, skb, NULL, NULL, 
 				  "ip_ct_tcp: invalid packet ignored ");
@@ -904,7 +903,7 @@
 		DEBUGP("ip_ct_tcp: Invalid dir=%i index=%u ostate=%u\n",
 		       dir, get_conntrack_index(th),
 		       old_state);
-		WRITE_UNLOCK(&tcp_lock);
+		write_unlock_bh(&tcp_lock);
 		if (LOG_INVALID(IPPROTO_TCP))
 			nf_log_packet(PF_INET, 0, skb, NULL, NULL, 
 				  "ip_ct_tcp: invalid state ");
@@ -918,13 +917,13 @@
 		    	     conntrack->proto.tcp.seen[dir].td_end)) {	
 		    	/* Attempt to reopen a closed connection.
 		    	* Delete this connection and look up again. */
-		    	WRITE_UNLOCK(&tcp_lock);
+		    	write_unlock_bh(&tcp_lock);
 		    	if (del_timer(&conntrack->timeout))
 		    		conntrack->timeout.function((unsigned long)
 		    					    conntrack);
 		    	return -NF_REPEAT;
 		} else {
-			WRITE_UNLOCK(&tcp_lock);
+			write_unlock_bh(&tcp_lock);
 			if (LOG_INVALID(IPPROTO_TCP))
 				nf_log_packet(PF_INET, 0, skb, NULL, NULL,
 				              "ip_ct_tcp: invalid SYN");
@@ -949,7 +948,7 @@
 
 	if (!tcp_in_window(&conntrack->proto.tcp, dir, index, 
 			   skb, iph, th)) {
-		WRITE_UNLOCK(&tcp_lock);
+		write_unlock_bh(&tcp_lock);
 		return -NF_ACCEPT;
 	}
     in_window:
@@ -972,7 +971,7 @@
 	timeout = conntrack->proto.tcp.retrans >= ip_ct_tcp_max_retrans
 		  && *tcp_timeouts[new_state] > ip_ct_tcp_timeout_max_retrans
 		  ? ip_ct_tcp_timeout_max_retrans : *tcp_timeouts[new_state];
-	WRITE_UNLOCK(&tcp_lock);
+	write_unlock_bh(&tcp_lock);
 
 	if (!test_bit(IPS_SEEN_REPLY_BIT, &conntrack->status)) {
 		/* If only reply is a RST, we can consider ourselves not to
diff --git a/net/ipv4/netfilter/ip_conntrack_proto_udp.c b/net/ipv4/netfilter/ip_conntrack_proto_udp.c
index 5bc28a2..8c1eaba 100644
--- a/net/ipv4/netfilter/ip_conntrack_proto_udp.c
+++ b/net/ipv4/netfilter/ip_conntrack_proto_udp.c
@@ -120,6 +120,7 @@
 	 * and moreover root might send raw packets.
 	 * FIXME: Source route IP option packets --RR */
 	if (hooknum == NF_IP_PRE_ROUTING
+	    && skb->ip_summed != CHECKSUM_UNNECESSARY
 	    && csum_tcpudp_magic(iph->saddr, iph->daddr, udplen, IPPROTO_UDP,
 			         skb->ip_summed == CHECKSUM_HW ? skb->csum
 			      	 : skb_checksum(skb, iph->ihl*4, udplen, 0))) {
diff --git a/net/ipv4/netfilter/ip_conntrack_standalone.c b/net/ipv4/netfilter/ip_conntrack_standalone.c
index bc59f7b..42dc951 100644
--- a/net/ipv4/netfilter/ip_conntrack_standalone.c
+++ b/net/ipv4/netfilter/ip_conntrack_standalone.c
@@ -28,8 +28,8 @@
 #include <net/checksum.h>
 #include <net/ip.h>
 
-#define ASSERT_READ_LOCK(x) MUST_BE_READ_LOCKED(&ip_conntrack_lock)
-#define ASSERT_WRITE_LOCK(x) MUST_BE_WRITE_LOCKED(&ip_conntrack_lock)
+#define ASSERT_READ_LOCK(x)
+#define ASSERT_WRITE_LOCK(x)
 
 #include <linux/netfilter_ipv4/ip_conntrack.h>
 #include <linux/netfilter_ipv4/ip_conntrack_protocol.h>
@@ -119,7 +119,7 @@
 
 static void *ct_seq_start(struct seq_file *seq, loff_t *pos)
 {
-	READ_LOCK(&ip_conntrack_lock);
+	read_lock_bh(&ip_conntrack_lock);
 	return ct_get_idx(seq, *pos);
 }
 
@@ -131,7 +131,7 @@
   
 static void ct_seq_stop(struct seq_file *s, void *v)
 {
-	READ_UNLOCK(&ip_conntrack_lock);
+	read_unlock_bh(&ip_conntrack_lock);
 }
  
 static int ct_seq_show(struct seq_file *s, void *v)
@@ -140,7 +140,7 @@
 	const struct ip_conntrack *conntrack = tuplehash_to_ctrack(hash);
 	struct ip_conntrack_protocol *proto;
 
-	MUST_BE_READ_LOCKED(&ip_conntrack_lock);
+	ASSERT_READ_LOCK(&ip_conntrack_lock);
 	IP_NF_ASSERT(conntrack);
 
 	/* we only want to print DIR_ORIGINAL */
@@ -239,7 +239,7 @@
 
 	/* strange seq_file api calls stop even if we fail,
 	 * thus we need to grab lock since stop unlocks */
-	READ_LOCK(&ip_conntrack_lock);
+	read_lock_bh(&ip_conntrack_lock);
 
 	if (list_empty(e))
 		return NULL;
@@ -267,7 +267,7 @@
 
 static void exp_seq_stop(struct seq_file *s, void *v)
 {
-	READ_UNLOCK(&ip_conntrack_lock);
+	read_unlock_bh(&ip_conntrack_lock);
 }
 
 static int exp_seq_show(struct seq_file *s, void *v)
@@ -921,22 +921,22 @@
 {
 	int ret = 0;
 
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	if (ip_ct_protos[proto->proto] != &ip_conntrack_generic_protocol) {
 		ret = -EBUSY;
 		goto out;
 	}
 	ip_ct_protos[proto->proto] = proto;
  out:
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 	return ret;
 }
 
 void ip_conntrack_protocol_unregister(struct ip_conntrack_protocol *proto)
 {
-	WRITE_LOCK(&ip_conntrack_lock);
+	write_lock_bh(&ip_conntrack_lock);
 	ip_ct_protos[proto->proto] = &ip_conntrack_generic_protocol;
-	WRITE_UNLOCK(&ip_conntrack_lock);
+	write_unlock_bh(&ip_conntrack_lock);
 	
 	/* Somebody could be still looking at the proto in bh. */
 	synchronize_net();
diff --git a/net/ipv4/netfilter/ip_nat_core.c b/net/ipv4/netfilter/ip_nat_core.c
index 9fc6f93..739b6dd 100644
--- a/net/ipv4/netfilter/ip_nat_core.c
+++ b/net/ipv4/netfilter/ip_nat_core.c
@@ -22,8 +22,8 @@
 #include <linux/udp.h>
 #include <linux/jhash.h>
 
-#define ASSERT_READ_LOCK(x) MUST_BE_READ_LOCKED(&ip_nat_lock)
-#define ASSERT_WRITE_LOCK(x) MUST_BE_WRITE_LOCKED(&ip_nat_lock)
+#define ASSERT_READ_LOCK(x)
+#define ASSERT_WRITE_LOCK(x)
 
 #include <linux/netfilter_ipv4/ip_conntrack.h>
 #include <linux/netfilter_ipv4/ip_conntrack_core.h>
@@ -41,7 +41,7 @@
 #define DEBUGP(format, args...)
 #endif
 
-DECLARE_RWLOCK(ip_nat_lock);
+DEFINE_RWLOCK(ip_nat_lock);
 
 /* Calculated at init based on memory size */
 static unsigned int ip_nat_htable_size;
@@ -65,9 +65,9 @@
 	if (!(conn->status & IPS_NAT_DONE_MASK))
 		return;
 
-	WRITE_LOCK(&ip_nat_lock);
+	write_lock_bh(&ip_nat_lock);
 	list_del(&conn->nat.info.bysource);
-	WRITE_UNLOCK(&ip_nat_lock);
+	write_unlock_bh(&ip_nat_lock);
 }
 
 /* We do checksum mangling, so if they were wrong before they're still
@@ -142,7 +142,7 @@
 	unsigned int h = hash_by_src(tuple);
 	struct ip_conntrack *ct;
 
-	READ_LOCK(&ip_nat_lock);
+	read_lock_bh(&ip_nat_lock);
 	list_for_each_entry(ct, &bysource[h], nat.info.bysource) {
 		if (same_src(ct, tuple)) {
 			/* Copy source part from reply tuple. */
@@ -151,12 +151,12 @@
 			result->dst = tuple->dst;
 
 			if (in_range(result, range)) {
-				READ_UNLOCK(&ip_nat_lock);
+				read_unlock_bh(&ip_nat_lock);
 				return 1;
 			}
 		}
 	}
-	READ_UNLOCK(&ip_nat_lock);
+	read_unlock_bh(&ip_nat_lock);
 	return 0;
 }
 
@@ -297,9 +297,9 @@
 		unsigned int srchash
 			= hash_by_src(&conntrack->tuplehash[IP_CT_DIR_ORIGINAL]
 				      .tuple);
-		WRITE_LOCK(&ip_nat_lock);
+		write_lock_bh(&ip_nat_lock);
 		list_add(&info->bysource, &bysource[srchash]);
-		WRITE_UNLOCK(&ip_nat_lock);
+		write_unlock_bh(&ip_nat_lock);
 	}
 
 	/* It's done. */
@@ -474,23 +474,23 @@
 {
 	int ret = 0;
 
-	WRITE_LOCK(&ip_nat_lock);
+	write_lock_bh(&ip_nat_lock);
 	if (ip_nat_protos[proto->protonum] != &ip_nat_unknown_protocol) {
 		ret = -EBUSY;
 		goto out;
 	}
 	ip_nat_protos[proto->protonum] = proto;
  out:
-	WRITE_UNLOCK(&ip_nat_lock);
+	write_unlock_bh(&ip_nat_lock);
 	return ret;
 }
 
 /* Noone stores the protocol anywhere; simply delete it. */
 void ip_nat_protocol_unregister(struct ip_nat_protocol *proto)
 {
-	WRITE_LOCK(&ip_nat_lock);
+	write_lock_bh(&ip_nat_lock);
 	ip_nat_protos[proto->protonum] = &ip_nat_unknown_protocol;
-	WRITE_UNLOCK(&ip_nat_lock);
+	write_unlock_bh(&ip_nat_lock);
 
 	/* Someone could be still looking at the proto in a bh. */
 	synchronize_net();
@@ -509,13 +509,13 @@
 		return -ENOMEM;
 
 	/* Sew in builtin protocols. */
-	WRITE_LOCK(&ip_nat_lock);
+	write_lock_bh(&ip_nat_lock);
 	for (i = 0; i < MAX_IP_NAT_PROTO; i++)
 		ip_nat_protos[i] = &ip_nat_unknown_protocol;
 	ip_nat_protos[IPPROTO_TCP] = &ip_nat_protocol_tcp;
 	ip_nat_protos[IPPROTO_UDP] = &ip_nat_protocol_udp;
 	ip_nat_protos[IPPROTO_ICMP] = &ip_nat_protocol_icmp;
-	WRITE_UNLOCK(&ip_nat_lock);
+	write_unlock_bh(&ip_nat_lock);
 
 	for (i = 0; i < ip_nat_htable_size; i++) {
 		INIT_LIST_HEAD(&bysource[i]);
diff --git a/net/ipv4/netfilter/ip_nat_helper.c b/net/ipv4/netfilter/ip_nat_helper.c
index 1637b96..158f34f 100644
--- a/net/ipv4/netfilter/ip_nat_helper.c
+++ b/net/ipv4/netfilter/ip_nat_helper.c
@@ -28,8 +28,8 @@
 #include <net/tcp.h>
 #include <net/udp.h>
 
-#define ASSERT_READ_LOCK(x) MUST_BE_READ_LOCKED(&ip_nat_lock)
-#define ASSERT_WRITE_LOCK(x) MUST_BE_WRITE_LOCKED(&ip_nat_lock)
+#define ASSERT_READ_LOCK(x)
+#define ASSERT_WRITE_LOCK(x)
 
 #include <linux/netfilter_ipv4/ip_conntrack.h>
 #include <linux/netfilter_ipv4/ip_conntrack_helper.h>
@@ -47,7 +47,7 @@
 #define DUMP_OFFSET(x)
 #endif
 
-static DECLARE_LOCK(ip_nat_seqofs_lock);
+static DEFINE_SPINLOCK(ip_nat_seqofs_lock);
 
 /* Setup TCP sequence correction given this change at this sequence */
 static inline void 
@@ -70,7 +70,7 @@
 	DEBUGP("ip_nat_resize_packet: Seq_offset before: ");
 	DUMP_OFFSET(this_way);
 
-	LOCK_BH(&ip_nat_seqofs_lock);
+	spin_lock_bh(&ip_nat_seqofs_lock);
 
 	/* SYN adjust. If it's uninitialized, or this is after last
 	 * correction, record it: we don't handle more than one
@@ -82,7 +82,7 @@
 		    this_way->offset_before = this_way->offset_after;
 		    this_way->offset_after += sizediff;
 	}
-	UNLOCK_BH(&ip_nat_seqofs_lock);
+	spin_unlock_bh(&ip_nat_seqofs_lock);
 
 	DEBUGP("ip_nat_resize_packet: Seq_offset after: ");
 	DUMP_OFFSET(this_way);
@@ -142,9 +142,6 @@
 	/* Transfer socket to new skb. */
 	if ((*pskb)->sk)
 		skb_set_owner_w(nskb, (*pskb)->sk);
-#ifdef CONFIG_NETFILTER_DEBUG
-	nskb->nf_debug = (*pskb)->nf_debug;
-#endif
 	kfree_skb(*pskb);
 	*pskb = nskb;
 	return 1;
diff --git a/net/ipv4/netfilter/ip_nat_rule.c b/net/ipv4/netfilter/ip_nat_rule.c
index 581f097..60d70fa 100644
--- a/net/ipv4/netfilter/ip_nat_rule.c
+++ b/net/ipv4/netfilter/ip_nat_rule.c
@@ -19,8 +19,8 @@
 #include <net/route.h>
 #include <linux/bitops.h>
 
-#define ASSERT_READ_LOCK(x) MUST_BE_READ_LOCKED(&ip_nat_lock)
-#define ASSERT_WRITE_LOCK(x) MUST_BE_WRITE_LOCKED(&ip_nat_lock)
+#define ASSERT_READ_LOCK(x)
+#define ASSERT_WRITE_LOCK(x)
 
 #include <linux/netfilter_ipv4/ip_tables.h>
 #include <linux/netfilter_ipv4/ip_nat.h>
diff --git a/net/ipv4/netfilter/ip_nat_standalone.c b/net/ipv4/netfilter/ip_nat_standalone.c
index 79f56f6..bc59d0d 100644
--- a/net/ipv4/netfilter/ip_nat_standalone.c
+++ b/net/ipv4/netfilter/ip_nat_standalone.c
@@ -31,8 +31,8 @@
 #include <net/checksum.h>
 #include <linux/spinlock.h>
 
-#define ASSERT_READ_LOCK(x) MUST_BE_READ_LOCKED(&ip_nat_lock)
-#define ASSERT_WRITE_LOCK(x) MUST_BE_WRITE_LOCKED(&ip_nat_lock)
+#define ASSERT_READ_LOCK(x)
+#define ASSERT_WRITE_LOCK(x)
 
 #include <linux/netfilter_ipv4/ip_nat.h>
 #include <linux/netfilter_ipv4/ip_nat_rule.h>
@@ -373,7 +373,6 @@
  cleanup_rule_init:
 	ip_nat_rule_cleanup();
  cleanup_nothing:
-	MUST_BE_READ_WRITE_UNLOCKED(&ip_nat_lock);
 	return ret;
 }
 
diff --git a/net/ipv4/netfilter/ip_tables.c b/net/ipv4/netfilter/ip_tables.c
index 8a54f92..c88dfcd 100644
--- a/net/ipv4/netfilter/ip_tables.c
+++ b/net/ipv4/netfilter/ip_tables.c
@@ -67,7 +67,6 @@
 /* Must have mutex */
 #define ASSERT_READ_LOCK(x) IP_NF_ASSERT(down_trylock(&ipt_mutex) != 0)
 #define ASSERT_WRITE_LOCK(x) IP_NF_ASSERT(down_trylock(&ipt_mutex) != 0)
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <linux/netfilter_ipv4/listhelp.h>
 
 #if 0
diff --git a/net/ipv4/netfilter/ipt_CLUSTERIP.c b/net/ipv4/netfilter/ipt_CLUSTERIP.c
index 0f12e3a..dc4362b 100644
--- a/net/ipv4/netfilter/ipt_CLUSTERIP.c
+++ b/net/ipv4/netfilter/ipt_CLUSTERIP.c
@@ -29,7 +29,6 @@
 #include <linux/netfilter_ipv4/ip_tables.h>
 #include <linux/netfilter_ipv4/ipt_CLUSTERIP.h>
 #include <linux/netfilter_ipv4/ip_conntrack.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 #define CLUSTERIP_VERSION "0.6"
 
@@ -41,6 +40,8 @@
 #define DEBUGP
 #endif
 
+#define ASSERT_READ_LOCK(x)
+
 MODULE_LICENSE("GPL");
 MODULE_AUTHOR("Harald Welte <laforge@netfilter.org>");
 MODULE_DESCRIPTION("iptables target for CLUSTERIP");
@@ -67,7 +68,7 @@
 
 /* clusterip_lock protects the clusterip_configs list _AND_ the configurable
  * data within all structurses (num_local_nodes, local_nodes[]) */
-static DECLARE_RWLOCK(clusterip_lock);
+static DEFINE_RWLOCK(clusterip_lock);
 
 #ifdef CONFIG_PROC_FS
 static struct file_operations clusterip_proc_fops;
@@ -82,9 +83,9 @@
 static inline void
 clusterip_config_put(struct clusterip_config *c) {
 	if (atomic_dec_and_test(&c->refcount)) {
-		WRITE_LOCK(&clusterip_lock);
+		write_lock_bh(&clusterip_lock);
 		list_del(&c->list);
-		WRITE_UNLOCK(&clusterip_lock);
+		write_unlock_bh(&clusterip_lock);
 		dev_mc_delete(c->dev, c->clustermac, ETH_ALEN, 0);
 		dev_put(c->dev);
 		kfree(c);
@@ -97,7 +98,7 @@
 {
 	struct list_head *pos;
 
-	MUST_BE_READ_LOCKED(&clusterip_lock);
+	ASSERT_READ_LOCK(&clusterip_lock);
 	list_for_each(pos, &clusterip_configs) {
 		struct clusterip_config *c = list_entry(pos, 
 					struct clusterip_config, list);
@@ -114,14 +115,14 @@
 {
 	struct clusterip_config *c;
 
-	READ_LOCK(&clusterip_lock);
+	read_lock_bh(&clusterip_lock);
 	c = __clusterip_config_find(clusterip);
 	if (!c) {
-		READ_UNLOCK(&clusterip_lock);
+		read_unlock_bh(&clusterip_lock);
 		return NULL;
 	}
 	atomic_inc(&c->refcount);
-	READ_UNLOCK(&clusterip_lock);
+	read_unlock_bh(&clusterip_lock);
 
 	return c;
 }
@@ -160,9 +161,9 @@
 	c->pde->data = c;
 #endif
 
-	WRITE_LOCK(&clusterip_lock);
+	write_lock_bh(&clusterip_lock);
 	list_add(&c->list, &clusterip_configs);
-	WRITE_UNLOCK(&clusterip_lock);
+	write_unlock_bh(&clusterip_lock);
 
 	return c;
 }
@@ -172,25 +173,25 @@
 {
 	int i;
 
-	WRITE_LOCK(&clusterip_lock);
+	write_lock_bh(&clusterip_lock);
 
 	if (c->num_local_nodes >= CLUSTERIP_MAX_NODES
 	    || nodenum > CLUSTERIP_MAX_NODES) {
-		WRITE_UNLOCK(&clusterip_lock);
+		write_unlock_bh(&clusterip_lock);
 		return 1;
 	}
 
 	/* check if we alrady have this number in our array */
 	for (i = 0; i < c->num_local_nodes; i++) {
 		if (c->local_nodes[i] == nodenum) {
-			WRITE_UNLOCK(&clusterip_lock);
+			write_unlock_bh(&clusterip_lock);
 			return 1;
 		}
 	}
 
 	c->local_nodes[c->num_local_nodes++] = nodenum;
 
-	WRITE_UNLOCK(&clusterip_lock);
+	write_unlock_bh(&clusterip_lock);
 	return 0;
 }
 
@@ -199,10 +200,10 @@
 {
 	int i;
 
-	WRITE_LOCK(&clusterip_lock);
+	write_lock_bh(&clusterip_lock);
 
 	if (c->num_local_nodes <= 1 || nodenum > CLUSTERIP_MAX_NODES) {
-		WRITE_UNLOCK(&clusterip_lock);
+		write_unlock_bh(&clusterip_lock);
 		return 1;
 	}
 		
@@ -211,12 +212,12 @@
 			int size = sizeof(u_int16_t)*(c->num_local_nodes-(i+1));
 			memmove(&c->local_nodes[i], &c->local_nodes[i+1], size);
 			c->num_local_nodes--;
-			WRITE_UNLOCK(&clusterip_lock);
+			write_unlock_bh(&clusterip_lock);
 			return 0;
 		}
 	}
 
-	WRITE_UNLOCK(&clusterip_lock);
+	write_unlock_bh(&clusterip_lock);
 	return 1;
 }
 
@@ -286,21 +287,21 @@
 {
 	int i;
 
-	READ_LOCK(&clusterip_lock);
+	read_lock_bh(&clusterip_lock);
 
 	if (config->num_local_nodes == 0) {
-		READ_UNLOCK(&clusterip_lock);
+		read_unlock_bh(&clusterip_lock);
 		return 0;
 	}
 
 	for (i = 0; i < config->num_local_nodes; i++) {
 		if (config->local_nodes[i] == hash) {
-			READ_UNLOCK(&clusterip_lock);
+			read_unlock_bh(&clusterip_lock);
 			return 1;
 		}
 	}
 
-	READ_UNLOCK(&clusterip_lock);
+	read_unlock_bh(&clusterip_lock);
 
 	return 0;
 }
@@ -578,7 +579,7 @@
 	struct clusterip_config *c = pde->data;
 	unsigned int *nodeidx;
 
-	READ_LOCK(&clusterip_lock);
+	read_lock_bh(&clusterip_lock);
 	if (*pos >= c->num_local_nodes)
 		return NULL;
 
@@ -608,7 +609,7 @@
 {
 	kfree(v);
 
-	READ_UNLOCK(&clusterip_lock);
+	read_unlock_bh(&clusterip_lock);
 }
 
 static int clusterip_seq_show(struct seq_file *s, void *v)
diff --git a/net/ipv4/netfilter/ipt_MASQUERADE.c b/net/ipv4/netfilter/ipt_MASQUERADE.c
index 57e9f6c..91e7450 100644
--- a/net/ipv4/netfilter/ipt_MASQUERADE.c
+++ b/net/ipv4/netfilter/ipt_MASQUERADE.c
@@ -33,7 +33,7 @@
 #endif
 
 /* Lock protects masq region inside conntrack */
-static DECLARE_RWLOCK(masq_lock);
+static DEFINE_RWLOCK(masq_lock);
 
 /* FIXME: Multiple targets. --RR */
 static int
@@ -103,9 +103,9 @@
 		return NF_DROP;
 	}
 
-	WRITE_LOCK(&masq_lock);
+	write_lock_bh(&masq_lock);
 	ct->nat.masq_index = out->ifindex;
-	WRITE_UNLOCK(&masq_lock);
+	write_unlock_bh(&masq_lock);
 
 	/* Transfer from original range. */
 	newrange = ((struct ip_nat_range)
@@ -122,9 +122,9 @@
 {
 	int ret;
 
-	READ_LOCK(&masq_lock);
+	read_lock_bh(&masq_lock);
 	ret = (i->nat.masq_index == (int)(long)ifindex);
-	READ_UNLOCK(&masq_lock);
+	read_unlock_bh(&masq_lock);
 
 	return ret;
 }
diff --git a/net/ipv4/netfilter/ipt_REJECT.c b/net/ipv4/netfilter/ipt_REJECT.c
index 266d649..9156964 100644
--- a/net/ipv4/netfilter/ipt_REJECT.c
+++ b/net/ipv4/netfilter/ipt_REJECT.c
@@ -104,10 +104,12 @@
 static void send_reset(struct sk_buff *oldskb, int hook)
 {
 	struct sk_buff *nskb;
+	struct iphdr *iph = oldskb->nh.iph;
 	struct tcphdr _otcph, *oth, *tcph;
 	struct rtable *rt;
 	u_int16_t tmp_port;
 	u_int32_t tmp_addr;
+	unsigned int tcplen;
 	int needs_ack;
 	int hh_len;
 
@@ -124,7 +126,16 @@
 	if (oth->rst)
 		return;
 
-	/* FIXME: Check checksum --RR */
+	/* Check checksum */
+	tcplen = oldskb->len - iph->ihl * 4;
+	if (((hook != NF_IP_LOCAL_IN && oldskb->ip_summed != CHECKSUM_HW) ||
+	     (hook == NF_IP_LOCAL_IN &&
+	      oldskb->ip_summed != CHECKSUM_UNNECESSARY)) &&
+	    csum_tcpudp_magic(iph->saddr, iph->daddr, tcplen, IPPROTO_TCP,
+	                      oldskb->ip_summed == CHECKSUM_HW ? oldskb->csum :
+	                      skb_checksum(oldskb, iph->ihl * 4, tcplen, 0)))
+		return;
+
 	if ((rt = route_reverse(oldskb, oth, hook)) == NULL)
 		return;
 
diff --git a/net/ipv4/netfilter/ipt_ULOG.c b/net/ipv4/netfilter/ipt_ULOG.c
index 6f2cefb..52a0076 100644
--- a/net/ipv4/netfilter/ipt_ULOG.c
+++ b/net/ipv4/netfilter/ipt_ULOG.c
@@ -56,7 +56,6 @@
 #include <linux/netfilter.h>
 #include <linux/netfilter_ipv4/ip_tables.h>
 #include <linux/netfilter_ipv4/ipt_ULOG.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <net/sock.h>
 #include <linux/bitops.h>
 
@@ -99,8 +98,8 @@
 
 static ulog_buff_t ulog_buffers[ULOG_MAXNLGROUPS];	/* array of buffers */
 
-static struct sock *nflognl;	/* our socket */
-static DECLARE_LOCK(ulog_lock);	/* spinlock */
+static struct sock *nflognl;		/* our socket */
+static DEFINE_SPINLOCK(ulog_lock);	/* spinlock */
 
 /* send one ulog_buff_t to userspace */
 static void ulog_send(unsigned int nlgroupnum)
@@ -135,9 +134,9 @@
 
 	/* lock to protect against somebody modifying our structure
 	 * from ipt_ulog_target at the same time */
-	LOCK_BH(&ulog_lock);
+	spin_lock_bh(&ulog_lock);
 	ulog_send(data);
-	UNLOCK_BH(&ulog_lock);
+	spin_unlock_bh(&ulog_lock);
 }
 
 static struct sk_buff *ulog_alloc_skb(unsigned int size)
@@ -193,7 +192,7 @@
 
 	ub = &ulog_buffers[groupnum];
 	
-	LOCK_BH(&ulog_lock);
+	spin_lock_bh(&ulog_lock);
 
 	if (!ub->skb) {
 		if (!(ub->skb = ulog_alloc_skb(size)))
@@ -278,7 +277,7 @@
 		ulog_send(groupnum);
 	}
 
-	UNLOCK_BH(&ulog_lock);
+	spin_unlock_bh(&ulog_lock);
 
 	return;
 
@@ -288,7 +287,7 @@
 alloc_failure:
 	PRINTR("ipt_ULOG: Error building netlink message\n");
 
-	UNLOCK_BH(&ulog_lock);
+	spin_unlock_bh(&ulog_lock);
 }
 
 static unsigned int ipt_ulog_target(struct sk_buff **pskb,
diff --git a/net/ipv4/netfilter/ipt_hashlimit.c b/net/ipv4/netfilter/ipt_hashlimit.c
index f1937190..564b49b 100644
--- a/net/ipv4/netfilter/ipt_hashlimit.c
+++ b/net/ipv4/netfilter/ipt_hashlimit.c
@@ -37,7 +37,6 @@
 
 #include <linux/netfilter_ipv4/ip_tables.h>
 #include <linux/netfilter_ipv4/ipt_hashlimit.h>
-#include <linux/netfilter_ipv4/lockhelp.h>
 
 /* FIXME: this is just for IP_NF_ASSERRT */
 #include <linux/netfilter_ipv4/ip_conntrack.h>
@@ -92,7 +91,7 @@
 	struct hlist_head hash[0];	/* hashtable itself */
 };
 
-static DECLARE_LOCK(hashlimit_lock);	/* protects htables list */
+static DEFINE_SPINLOCK(hashlimit_lock);	/* protects htables list */
 static DECLARE_MUTEX(hlimit_mutex);	/* additional checkentry protection */
 static HLIST_HEAD(hashlimit_htables);
 static kmem_cache_t *hashlimit_cachep;
@@ -233,9 +232,9 @@
 	hinfo->timer.function = htable_gc;
 	add_timer(&hinfo->timer);
 
-	LOCK_BH(&hashlimit_lock);
+	spin_lock_bh(&hashlimit_lock);
 	hlist_add_head(&hinfo->node, &hashlimit_htables);
-	UNLOCK_BH(&hashlimit_lock);
+	spin_unlock_bh(&hashlimit_lock);
 
 	return 0;
 }
@@ -301,15 +300,15 @@
 	struct ipt_hashlimit_htable *hinfo;
 	struct hlist_node *pos;
 
-	LOCK_BH(&hashlimit_lock);
+	spin_lock_bh(&hashlimit_lock);
 	hlist_for_each_entry(hinfo, pos, &hashlimit_htables, node) {
 		if (!strcmp(name, hinfo->pde->name)) {
 			atomic_inc(&hinfo->use);
-			UNLOCK_BH(&hashlimit_lock);
+			spin_unlock_bh(&hashlimit_lock);
 			return hinfo;
 		}
 	}
-	UNLOCK_BH(&hashlimit_lock);
+	spin_unlock_bh(&hashlimit_lock);
 
 	return NULL;
 }
@@ -317,9 +316,9 @@
 static void htable_put(struct ipt_hashlimit_htable *hinfo)
 {
 	if (atomic_dec_and_test(&hinfo->use)) {
-		LOCK_BH(&hashlimit_lock);
+		spin_lock_bh(&hashlimit_lock);
 		hlist_del(&hinfo->node);
-		UNLOCK_BH(&hashlimit_lock);
+		spin_unlock_bh(&hashlimit_lock);
 		htable_destroy(hinfo);
 	}
 }
diff --git a/net/ipv4/netfilter/ipt_helper.c b/net/ipv4/netfilter/ipt_helper.c
index 33fdf36..3e7dd01 100644
--- a/net/ipv4/netfilter/ipt_helper.c
+++ b/net/ipv4/netfilter/ipt_helper.c
@@ -53,7 +53,7 @@
 		return ret;
 	}
 
-	READ_LOCK(&ip_conntrack_lock);
+	read_lock_bh(&ip_conntrack_lock);
 	if (!ct->master->helper) {
 		DEBUGP("ipt_helper: master ct %p has no helper\n", 
 			exp->expectant);
@@ -69,7 +69,7 @@
 		ret ^= !strncmp(ct->master->helper->name, info->name, 
 		                strlen(ct->master->helper->name));
 out_unlock:
-	READ_UNLOCK(&ip_conntrack_lock);
+	read_unlock_bh(&ip_conntrack_lock);
 	return ret;
 }
 
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
index 47a30c3..14f5c53 100644
--- a/net/ipv6/addrconf.c
+++ b/net/ipv6/addrconf.c
@@ -695,7 +695,7 @@
 
 		if (rt && ((rt->rt6i_flags & (RTF_GATEWAY | RTF_DEFAULT)) == 0)) {
 			if (onlink == 0) {
-				ip6_del_rt(rt, NULL, NULL);
+				ip6_del_rt(rt, NULL, NULL, NULL);
 				rt = NULL;
 			} else if (!(rt->rt6i_flags & RTF_EXPIRES)) {
 				rt->rt6i_expires = expires;
@@ -1340,7 +1340,7 @@
 	if (dev->type == ARPHRD_SIT && (dev->flags&IFF_POINTOPOINT))
 		rtmsg.rtmsg_flags |= RTF_NONEXTHOP;
 
-	ip6_route_add(&rtmsg, NULL, NULL);
+	ip6_route_add(&rtmsg, NULL, NULL, NULL);
 }
 
 /* Create "default" multicast route to the interface */
@@ -1357,7 +1357,7 @@
 	rtmsg.rtmsg_ifindex = dev->ifindex;
 	rtmsg.rtmsg_flags = RTF_UP;
 	rtmsg.rtmsg_type = RTMSG_NEWROUTE;
-	ip6_route_add(&rtmsg, NULL, NULL);
+	ip6_route_add(&rtmsg, NULL, NULL, NULL);
 }
 
 static void sit_route_add(struct net_device *dev)
@@ -1374,7 +1374,7 @@
 	rtmsg.rtmsg_flags	= RTF_UP|RTF_NONEXTHOP;
 	rtmsg.rtmsg_ifindex	= dev->ifindex;
 
-	ip6_route_add(&rtmsg, NULL, NULL);
+	ip6_route_add(&rtmsg, NULL, NULL, NULL);
 }
 
 static void addrconf_add_lroute(struct net_device *dev)
@@ -1467,7 +1467,7 @@
 		if (rt && ((rt->rt6i_flags & (RTF_GATEWAY | RTF_DEFAULT)) == 0)) {
 			if (rt->rt6i_flags&RTF_EXPIRES) {
 				if (valid_lft == 0) {
-					ip6_del_rt(rt, NULL, NULL);
+					ip6_del_rt(rt, NULL, NULL, NULL);
 					rt = NULL;
 				} else {
 					rt->rt6i_expires = rt_expires;
@@ -3094,7 +3094,7 @@
 	switch (event) {
 	case RTM_NEWADDR:
 		dst_hold(&ifp->rt->u.dst);
-		if (ip6_ins_rt(ifp->rt, NULL, NULL))
+		if (ip6_ins_rt(ifp->rt, NULL, NULL, NULL))
 			dst_release(&ifp->rt->u.dst);
 		if (ifp->idev->cnf.forwarding)
 			addrconf_join_anycast(ifp);
@@ -3104,7 +3104,7 @@
 			addrconf_leave_anycast(ifp);
 		addrconf_leave_solict(ifp->idev, &ifp->addr);
 		dst_hold(&ifp->rt->u.dst);
-		if (ip6_del_rt(ifp->rt, NULL, NULL))
+		if (ip6_del_rt(ifp->rt, NULL, NULL, NULL))
 			dst_free(&ifp->rt->u.dst);
 		else
 			dst_release(&ifp->rt->u.dst);
diff --git a/net/ipv6/anycast.c b/net/ipv6/anycast.c
index 5d22ca3..6b72940 100644
--- a/net/ipv6/anycast.c
+++ b/net/ipv6/anycast.c
@@ -337,7 +337,7 @@
 	write_unlock_bh(&idev->lock);
 
 	dst_hold(&rt->u.dst);
-	if (ip6_ins_rt(rt, NULL, NULL))
+	if (ip6_ins_rt(rt, NULL, NULL, NULL))
 		dst_release(&rt->u.dst);
 
 	addrconf_join_solict(dev, &aca->aca_addr);
@@ -380,7 +380,7 @@
 	addrconf_leave_solict(idev, &aca->aca_addr);
 
 	dst_hold(&aca->aca_rt->u.dst);
-	if (ip6_del_rt(aca->aca_rt, NULL, NULL))
+	if (ip6_del_rt(aca->aca_rt, NULL, NULL, NULL))
 		dst_free(&aca->aca_rt->u.dst);
 	else
 		dst_release(&aca->aca_rt->u.dst);
diff --git a/net/ipv6/ip6_fib.c b/net/ipv6/ip6_fib.c
index 405740b..1b354aa 100644
--- a/net/ipv6/ip6_fib.c
+++ b/net/ipv6/ip6_fib.c
@@ -394,7 +394,7 @@
  */
 
 static int fib6_add_rt2node(struct fib6_node *fn, struct rt6_info *rt,
-    struct nlmsghdr *nlh)
+		struct nlmsghdr *nlh,  struct netlink_skb_parms *req)
 {
 	struct rt6_info *iter = NULL;
 	struct rt6_info **ins;
@@ -449,7 +449,7 @@
 	*ins = rt;
 	rt->rt6i_node = fn;
 	atomic_inc(&rt->rt6i_ref);
-	inet6_rt_notify(RTM_NEWROUTE, rt, nlh);
+	inet6_rt_notify(RTM_NEWROUTE, rt, nlh, req);
 	rt6_stats.fib_rt_entries++;
 
 	if ((fn->fn_flags & RTN_RTINFO) == 0) {
@@ -479,7 +479,8 @@
  *	with source addr info in sub-trees
  */
 
-int fib6_add(struct fib6_node *root, struct rt6_info *rt, struct nlmsghdr *nlh, void *_rtattr)
+int fib6_add(struct fib6_node *root, struct rt6_info *rt, 
+		struct nlmsghdr *nlh, void *_rtattr, struct netlink_skb_parms *req)
 {
 	struct fib6_node *fn;
 	int err = -ENOMEM;
@@ -552,7 +553,7 @@
 	}
 #endif
 
-	err = fib6_add_rt2node(fn, rt, nlh);
+	err = fib6_add_rt2node(fn, rt, nlh, req);
 
 	if (err == 0) {
 		fib6_start_gc(rt);
@@ -859,7 +860,7 @@
 }
 
 static void fib6_del_route(struct fib6_node *fn, struct rt6_info **rtp,
-    struct nlmsghdr *nlh, void *_rtattr)
+    struct nlmsghdr *nlh, void *_rtattr, struct netlink_skb_parms *req)
 {
 	struct fib6_walker_t *w;
 	struct rt6_info *rt = *rtp;
@@ -915,11 +916,11 @@
 		if (atomic_read(&rt->rt6i_ref) != 1) BUG();
 	}
 
-	inet6_rt_notify(RTM_DELROUTE, rt, nlh);
+	inet6_rt_notify(RTM_DELROUTE, rt, nlh, req);
 	rt6_release(rt);
 }
 
-int fib6_del(struct rt6_info *rt, struct nlmsghdr *nlh, void *_rtattr)
+int fib6_del(struct rt6_info *rt, struct nlmsghdr *nlh, void *_rtattr, struct netlink_skb_parms *req)
 {
 	struct fib6_node *fn = rt->rt6i_node;
 	struct rt6_info **rtp;
@@ -944,7 +945,7 @@
 
 	for (rtp = &fn->leaf; *rtp; rtp = &(*rtp)->u.next) {
 		if (*rtp == rt) {
-			fib6_del_route(fn, rtp, nlh, _rtattr);
+			fib6_del_route(fn, rtp, nlh, _rtattr, req);
 			return 0;
 		}
 	}
@@ -1073,7 +1074,7 @@
 		res = c->func(rt, c->arg);
 		if (res < 0) {
 			w->leaf = rt;
-			res = fib6_del(rt, NULL, NULL);
+			res = fib6_del(rt, NULL, NULL, NULL);
 			if (res) {
 #if RT6_DEBUG >= 2
 				printk(KERN_DEBUG "fib6_clean_node: del failed: rt=%p@%p err=%d\n", rt, rt->rt6i_node, res);
diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c
index b78a535..06e7cda 100644
--- a/net/ipv6/ip6_output.c
+++ b/net/ipv6/ip6_output.c
@@ -484,9 +484,6 @@
 	to->nf_bridge = from->nf_bridge;
 	nf_bridge_get(to->nf_bridge);
 #endif
-#ifdef CONFIG_NETFILTER_DEBUG
-	to->nf_debug = from->nf_debug;
-#endif
 #endif
 }
 
diff --git a/net/ipv6/ipv6_sockglue.c b/net/ipv6/ipv6_sockglue.c
index 279ab86..f3ef4c3 100644
--- a/net/ipv6/ipv6_sockglue.c
+++ b/net/ipv6/ipv6_sockglue.c
@@ -423,11 +423,12 @@
 			psin6 = (struct sockaddr_in6 *)&greqs.gsr_group;
 			retv = ipv6_sock_mc_join(sk, greqs.gsr_interface,
 				&psin6->sin6_addr);
-			if (retv)
+			/* prior join w/ different source is ok */
+			if (retv && retv != -EADDRINUSE)
 				break;
 			omode = MCAST_INCLUDE;
 			add = 1;
-		} else /*IP_DROP_SOURCE_MEMBERSHIP */ {
+		} else /* MCAST_LEAVE_SOURCE_GROUP */ {
 			omode = MCAST_INCLUDE;
 			add = 0;
 		}
diff --git a/net/ipv6/mcast.c b/net/ipv6/mcast.c
index 393b6e6..562fcd1 100644
--- a/net/ipv6/mcast.c
+++ b/net/ipv6/mcast.c
@@ -188,6 +188,16 @@
 	if (!ipv6_addr_is_multicast(addr))
 		return -EINVAL;
 
+	read_lock_bh(&ipv6_sk_mc_lock);
+	for (mc_lst=np->ipv6_mc_list; mc_lst; mc_lst=mc_lst->next) {
+		if ((ifindex == 0 || mc_lst->ifindex == ifindex) &&
+		    ipv6_addr_equal(&mc_lst->addr, addr)) {
+			read_unlock_bh(&ipv6_sk_mc_lock);
+			return -EADDRINUSE;
+		}
+	}
+	read_unlock_bh(&ipv6_sk_mc_lock);
+
 	mc_lst = sock_kmalloc(sk, sizeof(struct ipv6_mc_socklist), GFP_KERNEL);
 
 	if (mc_lst == NULL)
@@ -349,6 +359,7 @@
 	struct ipv6_pinfo *inet6 = inet6_sk(sk);
 	struct ip6_sf_socklist *psl;
 	int i, j, rv;
+	int leavegroup = 0;
 	int err;
 
 	if (pgsr->gsr_group.ss_family != AF_INET6 ||
@@ -368,6 +379,7 @@
 
 	err = -EADDRNOTAVAIL;
 
+	read_lock_bh(&ipv6_sk_mc_lock);
 	for (pmc=inet6->ipv6_mc_list; pmc; pmc=pmc->next) {
 		if (pgsr->gsr_interface && pmc->ifindex != pgsr->gsr_interface)
 			continue;
@@ -401,6 +413,12 @@
 		if (rv)		/* source not found */
 			goto done;
 
+		/* special case - (INCLUDE, empty) == LEAVE_GROUP */
+		if (psl->sl_count == 1 && omode == MCAST_INCLUDE) {
+			leavegroup = 1;
+			goto done;
+		}
+
 		/* update the interface filter */
 		ip6_mc_del_src(idev, group, omode, 1, source, 1);
 
@@ -453,9 +471,12 @@
 	/* update the interface list */
 	ip6_mc_add_src(idev, group, omode, 1, source, 1);
 done:
+	read_unlock_bh(&ipv6_sk_mc_lock);
 	read_unlock_bh(&idev->lock);
 	in6_dev_put(idev);
 	dev_put(dev);
+	if (leavegroup)
+		return ipv6_sock_mc_drop(sk, pgsr->gsr_interface, group);
 	return err;
 }
 
@@ -1280,15 +1301,6 @@
 		return NULL;
 
 	skb_reserve(skb, LL_RESERVED_SPACE(dev));
-	if (dev->hard_header) {
-		unsigned char ha[MAX_ADDR_LEN];
-
-		ndisc_mc_map(&mld2_all_mcr, ha, dev, 1);
-		if (dev->hard_header(skb, dev, ETH_P_IPV6,ha,NULL,size) < 0) {
-			kfree_skb(skb);
-			return NULL;
-		}
-	}
 
 	if (ipv6_get_lladdr(dev, &addr_buf)) {
 		/* <draft-ietf-magma-mld-source-05.txt>:
@@ -1312,6 +1324,30 @@
 	return skb;
 }
 
+static inline int mld_dev_queue_xmit2(struct sk_buff *skb)
+{
+	struct net_device *dev = skb->dev;
+
+	if (dev->hard_header) {
+		unsigned char ha[MAX_ADDR_LEN];
+		int err;
+
+		ndisc_mc_map(&skb->nh.ipv6h->daddr, ha, dev, 1);
+		err = dev->hard_header(skb, dev, ETH_P_IPV6, ha, NULL, skb->len);
+		if (err < 0) {
+			kfree_skb(skb);
+			return err;
+		}
+	}
+	return dev_queue_xmit(skb);
+}
+
+static inline int mld_dev_queue_xmit(struct sk_buff *skb)
+{
+	return NF_HOOK(PF_INET6, NF_IP6_POST_ROUTING, skb, NULL, skb->dev,
+	               mld_dev_queue_xmit2);
+}
+
 static void mld_sendpack(struct sk_buff *skb)
 {
 	struct ipv6hdr *pip6 = skb->nh.ipv6h;
@@ -1329,7 +1365,7 @@
 	pmr->csum = csum_ipv6_magic(&pip6->saddr, &pip6->daddr, mldlen,
 		IPPROTO_ICMPV6, csum_partial(skb->h.raw, mldlen, 0));
 	err = NF_HOOK(PF_INET6, NF_IP6_LOCAL_OUT, skb, NULL, skb->dev,
-		dev_queue_xmit);
+		mld_dev_queue_xmit);
 	if (!err) {
 		ICMP6_INC_STATS(idev,ICMP6_MIB_OUTMSGS);
 		IP6_INC_STATS(IPSTATS_MIB_OUTMCASTPKTS);
@@ -1635,12 +1671,6 @@
 	}
 
 	skb_reserve(skb, LL_RESERVED_SPACE(dev));
-	if (dev->hard_header) {
-		unsigned char ha[MAX_ADDR_LEN];
-		ndisc_mc_map(snd_addr, ha, dev, 1);
-		if (dev->hard_header(skb, dev, ETH_P_IPV6, ha, NULL, full_len) < 0)
-			goto out;
-	}
 
 	if (ipv6_get_lladdr(dev, &addr_buf)) {
 		/* <draft-ietf-magma-mld-source-05.txt>:
@@ -1668,7 +1698,7 @@
 	idev = in6_dev_get(skb->dev);
 
 	err = NF_HOOK(PF_INET6, NF_IP6_LOCAL_OUT, skb, NULL, skb->dev,
-		dev_queue_xmit);
+		mld_dev_queue_xmit);
 	if (!err) {
 		if (type == ICMPV6_MGM_REDUCTION)
 			ICMP6_INC_STATS(idev, ICMP6_MIB_OUTGROUPMEMBREDUCTIONS);
@@ -1682,10 +1712,6 @@
 	if (likely(idev != NULL))
 		in6_dev_put(idev);
 	return;
-
-out:
-	IP6_INC_STATS(IPSTATS_MIB_OUTDISCARDS);
-	kfree_skb(skb);
 }
 
 static int ip6_mc_del1_src(struct ifmcaddr6 *pmc, int sfmode,
diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c
index 7c291f4..7ae72d4 100644
--- a/net/ipv6/ndisc.c
+++ b/net/ipv6/ndisc.c
@@ -955,7 +955,7 @@
 			struct rt6_info *rt;
 			rt = rt6_get_dflt_router(saddr, dev);
 			if (rt)
-				ip6_del_rt(rt, NULL, NULL);
+				ip6_del_rt(rt, NULL, NULL, NULL);
 		}
 
 out:
@@ -1096,7 +1096,7 @@
 
 	if (rt && lifetime == 0) {
 		neigh_clone(neigh);
-		ip6_del_rt(rt, NULL, NULL);
+		ip6_del_rt(rt, NULL, NULL, NULL);
 		rt = NULL;
 	}
 
diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
index c735276..7303451 100644
--- a/net/ipv6/netfilter/ip6_tables.c
+++ b/net/ipv6/netfilter/ip6_tables.c
@@ -71,7 +71,6 @@
 /* Must have mutex */
 #define ASSERT_READ_LOCK(x) IP_NF_ASSERT(down_trylock(&ip6t_mutex) != 0)
 #define ASSERT_WRITE_LOCK(x) IP_NF_ASSERT(down_trylock(&ip6t_mutex) != 0)
-#include <linux/netfilter_ipv4/lockhelp.h>
 #include <linux/netfilter_ipv4/listhelp.h>
 
 #if 0
diff --git a/net/ipv6/netfilter/ip6t_LOG.c b/net/ipv6/netfilter/ip6t_LOG.c
index bfc3d01..c44685e 100644
--- a/net/ipv6/netfilter/ip6t_LOG.c
+++ b/net/ipv6/netfilter/ip6t_LOG.c
@@ -366,8 +366,6 @@
 		const char *level_string,
 		const char *prefix)
 {
-	struct ipv6hdr *ipv6h = skb->nh.ipv6h;
-
 	spin_lock_bh(&log_lock);
 	printk(level_string);
 	printk("%sIN=%s OUT=%s ",
@@ -377,39 +375,25 @@
 	if (in && !out) {
 		/* MAC logging for input chain only. */
 		printk("MAC=");
-		if (skb->dev && skb->dev->hard_header_len && skb->mac.raw != (void*)ipv6h) {
-			if (skb->dev->type != ARPHRD_SIT){
-			  int i;
-			  unsigned char *p = skb->mac.raw;
-			  for (i = 0; i < skb->dev->hard_header_len; i++,p++)
-				printk("%02x%c", *p,
-			       		i==skb->dev->hard_header_len - 1
-			       		? ' ':':');
-			} else {
-			  int i;
-			  unsigned char *p = skb->mac.raw;
-			  if ( p - (ETH_ALEN*2+2) > skb->head ){
-			    p -= (ETH_ALEN+2);
-			    for (i = 0; i < (ETH_ALEN); i++,p++)
-				printk("%02x%s", *p,
-					i == ETH_ALEN-1 ? "->" : ":");
-			    p -= (ETH_ALEN*2);
-			    for (i = 0; i < (ETH_ALEN); i++,p++)
-				printk("%02x%c", *p,
-					i == ETH_ALEN-1 ? ' ' : ':');
-			  }
-			  
-			  if ((skb->dev->addr_len == 4) &&
-			      skb->dev->hard_header_len > 20){
-			    printk("TUNNEL=");
-			    p = skb->mac.raw + 12;
-			    for (i = 0; i < 4; i++,p++)
-				printk("%3d%s", *p,
-					i == 3 ? "->" : ".");
-			    for (i = 0; i < 4; i++,p++)
-				printk("%3d%c", *p,
-					i == 3 ? ' ' : '.');
-			  }
+		if (skb->dev && skb->dev->hard_header_len &&
+		    skb->mac.raw != skb->nh.raw) {
+			unsigned char *p = skb->mac.raw;
+			int i;
+
+			if (skb->dev->type == ARPHRD_SIT &&
+			    (p -= ETH_HLEN) < skb->head)
+				p = NULL;
+
+			if (p != NULL)
+				for (i = 0; i < skb->dev->hard_header_len; i++)
+					printk("%02x", p[i]);
+			printk(" ");
+
+			if (skb->dev->type == ARPHRD_SIT) {
+				struct iphdr *iph = (struct iphdr *)skb->mac.raw;
+				printk("TUNNEL=%u.%u.%u.%u->%u.%u.%u.%u ",
+				       NIPQUAD(iph->saddr),
+				       NIPQUAD(iph->daddr));
 			}
 		} else
 			printk(" ");
diff --git a/net/ipv6/netfilter/ip6table_raw.c b/net/ipv6/netfilter/ip6table_raw.c
index 71407be..c2982ef 100644
--- a/net/ipv6/netfilter/ip6table_raw.c
+++ b/net/ipv6/netfilter/ip6table_raw.c
@@ -129,13 +129,15 @@
 	  .hook = ip6t_hook, 
 	  .pf = PF_INET6,
 	  .hooknum = NF_IP6_PRE_ROUTING,
-	  .priority = NF_IP6_PRI_FIRST
+	  .priority = NF_IP6_PRI_FIRST,
+	  .owner = THIS_MODULE,
 	},
 	{
 	  .hook = ip6t_hook, 
 	  .pf = PF_INET6, 
 	  .hooknum = NF_IP6_LOCAL_OUT,
-	  .priority = NF_IP6_PRI_FIRST
+	  .priority = NF_IP6_PRI_FIRST,
+	  .owner = THIS_MODULE,
 	},
 };
 
diff --git a/net/ipv6/route.c b/net/ipv6/route.c
index 1f5b226..878789b 100644
--- a/net/ipv6/route.c
+++ b/net/ipv6/route.c
@@ -384,12 +384,13 @@
    be destroyed.
  */
 
-int ip6_ins_rt(struct rt6_info *rt, struct nlmsghdr *nlh, void *_rtattr)
+int ip6_ins_rt(struct rt6_info *rt, struct nlmsghdr *nlh,
+		void *_rtattr, struct netlink_skb_parms *req)
 {
 	int err;
 
 	write_lock_bh(&rt6_lock);
-	err = fib6_add(&ip6_routing_table, rt, nlh, _rtattr);
+	err = fib6_add(&ip6_routing_table, rt, nlh, _rtattr, req);
 	write_unlock_bh(&rt6_lock);
 
 	return err;
@@ -400,7 +401,7 @@
  */
 
 static struct rt6_info *rt6_cow(struct rt6_info *ort, struct in6_addr *daddr,
-				struct in6_addr *saddr)
+				struct in6_addr *saddr, struct netlink_skb_parms *req)
 {
 	int err;
 	struct rt6_info *rt;
@@ -432,7 +433,7 @@
 
 		dst_hold(&rt->u.dst);
 
-		err = ip6_ins_rt(rt, NULL, NULL);
+		err = ip6_ins_rt(rt, NULL, NULL, req);
 		if (err == 0)
 			return rt;
 
@@ -491,7 +492,8 @@
 		read_unlock_bh(&rt6_lock);
 
 		nrt = rt6_cow(rt, &skb->nh.ipv6h->daddr,
-			      &skb->nh.ipv6h->saddr);
+			      &skb->nh.ipv6h->saddr,
+			      &NETLINK_CB(skb));
 
 		dst_release(&rt->u.dst);
 		rt = nrt;
@@ -551,7 +553,7 @@
 		dst_hold(&rt->u.dst);
 		read_unlock_bh(&rt6_lock);
 
-		nrt = rt6_cow(rt, &fl->fl6_dst, &fl->fl6_src);
+		nrt = rt6_cow(rt, &fl->fl6_dst, &fl->fl6_src, NULL);
 
 		dst_release(&rt->u.dst);
 		rt = nrt;
@@ -598,7 +600,7 @@
 
 	if (rt) {
 		if (rt->rt6i_flags & RTF_CACHE)
-			ip6_del_rt(rt, NULL, NULL);
+			ip6_del_rt(rt, NULL, NULL, NULL);
 		else
 			dst_release(dst);
 	}
@@ -787,7 +789,8 @@
  *
  */
 
-int ip6_route_add(struct in6_rtmsg *rtmsg, struct nlmsghdr *nlh, void *_rtattr)
+int ip6_route_add(struct in6_rtmsg *rtmsg, struct nlmsghdr *nlh, 
+		void *_rtattr, struct netlink_skb_parms *req)
 {
 	int err;
 	struct rtmsg *r;
@@ -974,7 +977,7 @@
 		rt->u.dst.metrics[RTAX_ADVMSS-1] = ipv6_advmss(dst_mtu(&rt->u.dst));
 	rt->u.dst.dev = dev;
 	rt->rt6i_idev = idev;
-	return ip6_ins_rt(rt, nlh, _rtattr);
+	return ip6_ins_rt(rt, nlh, _rtattr, req);
 
 out:
 	if (dev)
@@ -986,7 +989,7 @@
 	return err;
 }
 
-int ip6_del_rt(struct rt6_info *rt, struct nlmsghdr *nlh, void *_rtattr)
+int ip6_del_rt(struct rt6_info *rt, struct nlmsghdr *nlh, void *_rtattr, struct netlink_skb_parms *req)
 {
 	int err;
 
@@ -994,7 +997,7 @@
 
 	rt6_reset_dflt_pointer(NULL);
 
-	err = fib6_del(rt, nlh, _rtattr);
+	err = fib6_del(rt, nlh, _rtattr, req);
 	dst_release(&rt->u.dst);
 
 	write_unlock_bh(&rt6_lock);
@@ -1002,7 +1005,7 @@
 	return err;
 }
 
-static int ip6_route_del(struct in6_rtmsg *rtmsg, struct nlmsghdr *nlh, void *_rtattr)
+static int ip6_route_del(struct in6_rtmsg *rtmsg, struct nlmsghdr *nlh, void *_rtattr, struct netlink_skb_parms *req)
 {
 	struct fib6_node *fn;
 	struct rt6_info *rt;
@@ -1029,7 +1032,7 @@
 			dst_hold(&rt->u.dst);
 			read_unlock_bh(&rt6_lock);
 
-			return ip6_del_rt(rt, nlh, _rtattr);
+			return ip6_del_rt(rt, nlh, _rtattr, req);
 		}
 	}
 	read_unlock_bh(&rt6_lock);
@@ -1136,11 +1139,11 @@
 	nrt->u.dst.metrics[RTAX_MTU-1] = ipv6_get_mtu(neigh->dev);
 	nrt->u.dst.metrics[RTAX_ADVMSS-1] = ipv6_advmss(dst_mtu(&nrt->u.dst));
 
-	if (ip6_ins_rt(nrt, NULL, NULL))
+	if (ip6_ins_rt(nrt, NULL, NULL, NULL))
 		goto out;
 
 	if (rt->rt6i_flags&RTF_CACHE) {
-		ip6_del_rt(rt, NULL, NULL);
+		ip6_del_rt(rt, NULL, NULL, NULL);
 		return;
 	}
 
@@ -1204,7 +1207,7 @@
 	   2. It is gatewayed route or NONEXTHOP route. Action: clone it.
 	 */
 	if (!rt->rt6i_nexthop && !(rt->rt6i_flags & RTF_NONEXTHOP)) {
-		nrt = rt6_cow(rt, daddr, saddr);
+		nrt = rt6_cow(rt, daddr, saddr, NULL);
 		if (!nrt->u.dst.error) {
 			nrt->u.dst.metrics[RTAX_MTU-1] = pmtu;
 			if (allfrag)
@@ -1232,7 +1235,7 @@
 		nrt->u.dst.metrics[RTAX_MTU-1] = pmtu;
 		if (allfrag)
 			nrt->u.dst.metrics[RTAX_FEATURES-1] |= RTAX_FEATURE_ALLFRAG;
-		ip6_ins_rt(nrt, NULL, NULL);
+		ip6_ins_rt(nrt, NULL, NULL, NULL);
 	}
 
 out:
@@ -1305,7 +1308,7 @@
 
 	rtmsg.rtmsg_ifindex = dev->ifindex;
 
-	ip6_route_add(&rtmsg, NULL, NULL);
+	ip6_route_add(&rtmsg, NULL, NULL, NULL);
 	return rt6_get_dflt_router(gwaddr, dev);
 }
 
@@ -1323,7 +1326,7 @@
 
 			read_unlock_bh(&rt6_lock);
 
-			ip6_del_rt(rt, NULL, NULL);
+			ip6_del_rt(rt, NULL, NULL, NULL);
 
 			goto restart;
 		}
@@ -1349,10 +1352,10 @@
 		rtnl_lock();
 		switch (cmd) {
 		case SIOCADDRT:
-			err = ip6_route_add(&rtmsg, NULL, NULL);
+			err = ip6_route_add(&rtmsg, NULL, NULL, NULL);
 			break;
 		case SIOCDELRT:
-			err = ip6_route_del(&rtmsg, NULL, NULL);
+			err = ip6_route_del(&rtmsg, NULL, NULL, NULL);
 			break;
 		default:
 			err = -EINVAL;
@@ -1546,7 +1549,7 @@
 
 	if (inet6_rtm_to_rtmsg(r, arg, &rtmsg))
 		return -EINVAL;
-	return ip6_route_del(&rtmsg, nlh, arg);
+	return ip6_route_del(&rtmsg, nlh, arg, &NETLINK_CB(skb));
 }
 
 int inet6_rtm_newroute(struct sk_buff *skb, struct nlmsghdr* nlh, void *arg)
@@ -1556,7 +1559,7 @@
 
 	if (inet6_rtm_to_rtmsg(r, arg, &rtmsg))
 		return -EINVAL;
-	return ip6_route_add(&rtmsg, nlh, arg);
+	return ip6_route_add(&rtmsg, nlh, arg, &NETLINK_CB(skb));
 }
 
 struct rt6_rtnl_dump_arg
@@ -1566,12 +1569,9 @@
 };
 
 static int rt6_fill_node(struct sk_buff *skb, struct rt6_info *rt,
-			 struct in6_addr *dst,
-			 struct in6_addr *src,
-			 int iif,
-			 int type, u32 pid, u32 seq,
-			 struct nlmsghdr *in_nlh, int prefix,
-			 unsigned int flags)
+			 struct in6_addr *dst, struct in6_addr *src,
+			 int iif, int type, u32 pid, u32 seq,
+			 int prefix, unsigned int flags)
 {
 	struct rtmsg *rtm;
 	struct nlmsghdr  *nlh;
@@ -1585,10 +1585,6 @@
 		}
 	}
 
-	if (!pid && in_nlh) {
-		pid = in_nlh->nlmsg_pid;
-	}
-
 	nlh = NLMSG_NEW(skb, pid, seq, type, sizeof(*rtm), flags);
 	rtm = NLMSG_DATA(nlh);
 	rtm->rtm_family = AF_INET6;
@@ -1675,7 +1671,7 @@
 
 	return rt6_fill_node(arg->skb, rt, NULL, NULL, 0, RTM_NEWROUTE,
 		     NETLINK_CB(arg->cb->skb).pid, arg->cb->nlh->nlmsg_seq,
-		     NULL, prefix, NLM_F_MULTI);
+		     prefix, NLM_F_MULTI);
 }
 
 static int fib6_dump_node(struct fib6_walker_t *w)
@@ -1823,7 +1819,7 @@
 			    &fl.fl6_dst, &fl.fl6_src,
 			    iif,
 			    RTM_NEWROUTE, NETLINK_CB(in_skb).pid,
-			    nlh->nlmsg_seq, nlh, 0, 0);
+			    nlh->nlmsg_seq, 0, 0);
 	if (err < 0) {
 		err = -EMSGSIZE;
 		goto out_free;
@@ -1839,17 +1835,25 @@
 	goto out;	
 }
 
-void inet6_rt_notify(int event, struct rt6_info *rt, struct nlmsghdr *nlh)
+void inet6_rt_notify(int event, struct rt6_info *rt, struct nlmsghdr *nlh, 
+			struct netlink_skb_parms *req)
 {
 	struct sk_buff *skb;
 	int size = NLMSG_SPACE(sizeof(struct rtmsg)+256);
+	u32 pid = current->pid;
+	u32 seq = 0;
 
+	if (req)
+		pid = req->pid;
+	if (nlh)
+		seq = nlh->nlmsg_seq;
+	
 	skb = alloc_skb(size, gfp_any());
 	if (!skb) {
 		netlink_set_err(rtnl, 0, RTMGRP_IPV6_ROUTE, ENOBUFS);
 		return;
 	}
-	if (rt6_fill_node(skb, rt, NULL, NULL, 0, event, 0, 0, nlh, 0, 0) < 0) {
+	if (rt6_fill_node(skb, rt, NULL, NULL, 0, event, pid, seq, 0, 0) < 0) {
 		kfree_skb(skb);
 		netlink_set_err(rtnl, 0, RTMGRP_IPV6_ROUTE, EINVAL);
 		return;
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c
index db845cb..87302a4 100644
--- a/security/selinux/hooks.c
+++ b/security/selinux/hooks.c
@@ -1945,6 +1945,7 @@
 	} while (*in_end++);
 
 	copy_page(in_save, nosec_save);
+	free_page((unsigned long)nosec_save);
 out:
 	return rc;
 }
diff --git a/sound/oss/rme96xx.c b/sound/oss/rme96xx.c
index 76774bb..b4278ee 100644
--- a/sound/oss/rme96xx.c
+++ b/sound/oss/rme96xx.c
@@ -807,7 +807,7 @@
                 struct page* page, *last_page;
 
                 page = virt_to_page(buf);
-                last_page = virt_to_page(buf + (1 << pg));
+                last_page = page + (1 << pg);
                 DBG(printk("setting reserved bit\n"));
                 while (page < last_page) {
 			SetPageReserved(page);