## Automatically generated incremental diff
## From:   linux-2.4.21-bk33
## To:     linux-2.4.21-bk34
## Robot:  $Id: make-incremental-diff,v 1.11 2002/02/20 02:59:33 hpa Exp $

diff -urN linux-2.4.21-bk33/CREDITS linux-2.4.21-bk34/CREDITS
--- linux-2.4.21-bk33/CREDITS	2003-08-15 02:54:39.000000000 -0700
+++ linux-2.4.21-bk34/CREDITS	2003-08-15 02:54:45.000000000 -0700
@@ -3095,7 +3095,7 @@
 N: Geert Uytterhoeven
 E: geert@linux-m68k.org
 W: http://home.tvd.be/cr26864/
-P: 1024/EC4A1EE1 8B 88 38 35 88 1E 95 A1  CD 9E AE DC 4B 4A 2F 41
+P: 1024/862678A6 C51D 361C 0BD1 4C90 B275  C553 6EEA 11BA 8626 78A6
 D: m68k/Amiga and PPC/CHRP Longtrail coordinator
 D: Frame buffer device and XF68_FBDev maintainer
 D: m68k IDE maintainer
@@ -3104,8 +3104,8 @@
 D: Atari Falcon chipset IDE
 D: Amiga Gayle chipset IDE
 D: mipsel NEC DDB Vrc-5074
-S: C. Huysmansstraat 12
-S: B-3128 Baal
+S: Holsbeeksesteenweg 166
+S: B-3010 Kessel-Lo
 S: Belgium
 
 N: Petr Vandrovec
diff -urN linux-2.4.21-bk33/Makefile linux-2.4.21-bk34/Makefile
--- linux-2.4.21-bk33/Makefile	2003-08-15 02:54:39.000000000 -0700
+++ linux-2.4.21-bk34/Makefile	2003-08-15 02:54:45.000000000 -0700
@@ -1,7 +1,7 @@
 VERSION = 2
 PATCHLEVEL = 4
 SUBLEVEL = 21
-EXTRAVERSION = -bk33
+EXTRAVERSION = -bk34
 
 KERNELRELEASE=$(VERSION).$(PATCHLEVEL).$(SUBLEVEL)$(EXTRAVERSION)
 
diff -urN linux-2.4.21-bk33/arch/mips/dec/Makefile linux-2.4.21-bk34/arch/mips/dec/Makefile
--- linux-2.4.21-bk33/arch/mips/dec/Makefile	2002-11-28 15:53:09.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/Makefile	2003-08-15 02:54:46.000000000 -0700
@@ -12,9 +12,10 @@
 
 all: dec.o
 
-export-objs := setup.o wbflush.o
-obj-y	 := int-handler.o ioasic-irq.o kn02-irq.o reset.o rtc-dec.o setup.o \
-	time.o
+export-objs	:= rtc-dec.o setup.o wbflush.o
+
+obj-y		:= ecc-berr.o int-handler.o ioasic-irq.o kn02-irq.o reset.o \
+		   rtc-dec.o setup.o time.o
 
 obj-$(CONFIG_PROM_CONSOLE)	+= promcon.o
 obj-$(CONFIG_CPU_HAS_WB)	+= wbflush.o
diff -urN linux-2.4.21-bk33/arch/mips/dec/ecc-berr.c linux-2.4.21-bk34/arch/mips/dec/ecc-berr.c
--- linux-2.4.21-bk33/arch/mips/dec/ecc-berr.c	1969-12-31 16:00:00.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/ecc-berr.c	2003-08-15 02:54:46.000000000 -0700
@@ -0,0 +1,280 @@
+/*
+ *	linux/arch/mips/dec/ecc-berr.c
+ *
+ *	Bus error event handling code for systems equipped with ECC
+ *	handling logic, i.e. DECstation/DECsystem 5000/200 (KN02),
+ *	5000/240 (KN03), 5000/260 (KN05) and DECsystem 5900 (KN03),
+ *	5900/260 (KN05) systems.
+ *
+ *	Copyright (c) 2003  Maciej W. Rozycki
+ *
+ *	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.
+ */
+
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/spinlock.h>
+#include <linux/types.h>
+
+#include <asm/addrspace.h>
+#include <asm/bootinfo.h>
+#include <asm/cpu.h>
+#include <asm/processor.h>
+#include <asm/system.h>
+#include <asm/traps.h>
+
+#include <asm/dec/ecc.h>
+#include <asm/dec/kn02.h>
+#include <asm/dec/kn03.h>
+#include <asm/dec/kn05.h>
+
+static volatile u32 *kn0x_erraddr;
+static volatile u32 *kn0x_chksyn;
+
+static inline void dec_ecc_be_ack(void)
+{
+	*kn0x_erraddr = 0;			/* any write clears the IRQ */
+	iob();
+}
+
+static int dec_ecc_be_backend(struct pt_regs *regs, int is_fixup, int invoker)
+{
+	static const char excstr[] = "exception";
+	static const char intstr[] = "interrupt";
+	static const char cpustr[] = "CPU";
+	static const char dmastr[] = "DMA";
+	static const char readstr[] = "read";
+	static const char mreadstr[] = "memory read";
+	static const char writestr[] = "write";
+	static const char mwritstr[] = "partial memory write";
+	static const char timestr[] = "timeout";
+	static const char overstr[] = "overrun";
+	static const char eccstr[] = "ECC error";
+
+	const char *kind, *agent, *cycle, *event;
+	const char *status = "", *xbit = "", *fmt = "";
+	dma_addr_t address;
+	u16 syn = 0, sngl;
+
+	int i = 0;
+
+	u32 erraddr = *kn0x_erraddr;
+	u32 chksyn = *kn0x_chksyn;
+	int action = MIPS_BE_FATAL;
+
+	/* For non-ECC ack ASAP, so any subsequent errors get caught. */
+	if ((erraddr & (KN0X_EAR_VALID | KN0X_EAR_ECCERR)) == KN0X_EAR_VALID)
+		dec_ecc_be_ack();
+
+	kind = invoker ? intstr : excstr;
+
+	if (!(erraddr & KN0X_EAR_VALID)) {
+		/* No idea what happened. */
+		printk(KERN_ALERT "Unindentified bus error %s.\n", kind);
+		return action;
+	}
+
+	agent = (erraddr & KN0X_EAR_CPU) ? cpustr : dmastr;
+
+	if (erraddr & KN0X_EAR_ECCERR) {
+		/* An ECC error on a CPU or DMA transaction. */
+		cycle = (erraddr & KN0X_EAR_WRITE) ? mwritstr : mreadstr;
+		event = eccstr;
+	} else {
+		/* A CPU timeout or a DMA overrun. */
+		cycle = (erraddr & KN0X_EAR_WRITE) ? writestr : readstr;
+		event = (erraddr & KN0X_EAR_CPU) ? timestr : overstr;
+	}
+
+	address = erraddr & KN0X_EAR_ADDRESS;
+	/* For ECC errors on reads adjust for MT pipelining. */
+	if ((erraddr & (KN0X_EAR_WRITE | KN0X_EAR_ECCERR)) == KN0X_EAR_ECCERR)
+		address = (address & ~0xfffLL) | ((address - 5) & 0xfffLL);
+	address <<= 2;
+
+	/* Only CPU errors are fixable. */
+	if (erraddr & KN0X_EAR_CPU && is_fixup)
+		action = MIPS_BE_FIXUP;
+
+	if (erraddr & KN0X_EAR_ECCERR) {
+		static const u8 data_sbit[32] = {
+			0x4f, 0x4a, 0x52, 0x54, 0x57, 0x58, 0x5b, 0x5d,
+			0x23, 0x25, 0x26, 0x29, 0x2a, 0x2c, 0x31, 0x34,
+			0x0e, 0x0b, 0x13, 0x15, 0x16, 0x19, 0x1a, 0x1c,
+			0x62, 0x64, 0x67, 0x68, 0x6b, 0x6d, 0x70, 0x75,
+		};
+		static const u8 data_mbit[25] = {
+			0x07, 0x0d, 0x1f,
+			0x2f, 0x32, 0x37, 0x38, 0x3b, 0x3d, 0x3e,
+			0x43, 0x45, 0x46, 0x49, 0x4c, 0x51, 0x5e,
+			0x61, 0x6e, 0x73, 0x76, 0x79, 0x7a, 0x7c, 0x7f,
+		};
+		static const char sbestr[] = "corrected single";
+		static const char dbestr[] = "uncorrectable double";
+		static const char mbestr[] = "uncorrectable multiple";
+
+		if (!(address & 0x4))
+			syn = chksyn;			/* Low bank. */
+		else
+			syn = chksyn >> 16;		/* High bank. */
+
+		if (!(syn & KN0X_ESR_VLDLO)) {
+			/* Ack now, no rewrite will happen. */
+			dec_ecc_be_ack();
+
+			fmt = KERN_ALERT "%s" "invalid.\n";
+		} else {
+			sngl = syn & KN0X_ESR_SNGLO;
+			syn &= KN0X_ESR_SYNLO;
+
+			/*
+			 * Multibit errors may be tagged incorrectly;
+			 * check the syndrome explicitly.
+			 */
+			for (i = 0; i < 25; i++)
+				if (syn == data_mbit[i])
+					break;
+
+			if (i < 25) {
+				status = mbestr;
+			} else if (!sngl) {
+				status = dbestr;
+			} else {
+				volatile u32 *ptr = (void *)KSEG1ADDR(address);
+
+				*ptr = *ptr;		/* Rewrite. */
+				iob();
+
+				status = sbestr;
+				action = MIPS_BE_DISCARD;
+			}
+
+			/* Ack now, now we've rewritten (or not). */
+			dec_ecc_be_ack();
+
+			if (syn && syn == (syn & -syn)) {
+				if (syn == 0x01) {
+					fmt = KERN_ALERT "%s"
+					      "%#04x -- %s bit error "
+					      "at check bit C%s.\n";
+					xbit = "X";
+				} else {
+					fmt = KERN_ALERT "%s"
+					      "%#04x -- %s bit error "
+					      "at check bit C%s%u.\n";
+				}
+				i = syn >> 2;
+			} else {
+				for (i = 0; i < 32; i++)
+					if (syn == data_sbit[i])
+						break;
+				if (i < 32)
+					fmt = KERN_ALERT "%s"
+					      "%#04x -- %s bit error "
+					      "at data bit D%s%u.\n";
+				else
+					fmt = KERN_ALERT "%s"
+					      "%#04x -- %s bit error.\n";
+			}
+		}
+	}
+
+	if (action != MIPS_BE_FIXUP)
+		printk(KERN_ALERT "Bus error %s: %s %s %s at %#010lx.\n",
+			kind, agent, cycle, event, address);
+
+	if (action != MIPS_BE_FIXUP && erraddr & KN0X_EAR_ECCERR)
+		printk(fmt, "  ECC syndrome ", syn, status, xbit, i);
+
+	return action;
+}
+
+int dec_ecc_be_handler(struct pt_regs *regs, int is_fixup)
+{
+	return dec_ecc_be_backend(regs, is_fixup, 0);
+}
+
+void dec_ecc_be_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+{
+	int action = dec_ecc_be_backend(regs, 0, 1);
+
+	if (action == MIPS_BE_DISCARD)
+		return;
+
+	/*
+	 * FIXME: Find affected processes and kill them, otherwise we
+	 * must die.
+	 *
+	 * The interrupt is asynchronously delivered thus EPC and RA
+	 * may be irrelevant, but are printed for a reference.
+	 */
+	printk(KERN_ALERT "Fatal bus interrupt, epc == %08lx, ra == %08lx\n",
+	       regs->cp0_epc, regs->regs[31]);
+	die("Unrecoverable bus error", regs);
+}
+
+
+/*
+ * Initialization differs a bit between KN02 and KN03/KN05, so we
+ * need two variants.  Once set up, all systems can be handled the
+ * same way.
+ */
+static inline void dec_kn02_be_init(void)
+{
+	volatile u32 *csr = (void *)KN02_CSR_BASE;
+	unsigned long flags;
+
+	kn0x_erraddr = (void *)(KN02_SLOT_BASE + KN02_ERRADDR);
+	kn0x_chksyn = (void *)(KN02_SLOT_BASE + KN02_CHKSYN);
+
+	spin_lock_irqsave(&kn02_lock, flags);
+
+	/* Preset write-only bits of the Control Register cache. */
+	cached_kn02_csr = *csr | KN03_CSR_LEDS;
+
+	/* Set normal ECC detection and generation. */
+	cached_kn02_csr &= ~(KN02_CSR_DIAGCHK | KN02_CSR_DIAGGEN);
+	/* Enable ECC correction. */
+	cached_kn02_csr |= KN02_CSR_CORRECT;
+	*csr = cached_kn02_csr;
+	iob();
+
+	spin_unlock_irqrestore(&kn02_lock, flags);
+}
+
+static inline void dec_kn03_be_init(void)
+{
+	volatile u32 *mcr = (void *)(KN03_SLOT_BASE + IOASIC_MCR);
+	volatile u32 *mbcs = (void *)(KN03_SLOT_BASE + KN05_MB_CSR);
+
+	kn0x_erraddr = (void *)(KN03_SLOT_BASE + IOASIC_ERRADDR);
+	kn0x_chksyn = (void *)(KN03_SLOT_BASE + IOASIC_CHKSYN);
+			
+	/*
+	 * Set normal ECC detection and generation, enable ECC correction.
+	 * For KN05 we also need to make sure EE (?) is enabled in the MB.
+	 * Otherwise DBE/IBE exceptions would be masked but bus error
+	 * interrupts would still arrive, resulting in an inevitable crash
+	 * if get_dbe() triggers one.
+	 */
+	*mcr = (*mcr & ~(KN03_MCR_DIAGCHK | KN03_MCR_DIAGGEN)) |
+	       KN03_MCR_CORRECT;
+	if (current_cpu_data.cputype == CPU_R4400SC)
+		*mbcs |= KN05_MB_CSR_EE;
+	fast_iob();
+}
+
+void __init dec_ecc_be_init(void)
+{
+	if (mips_machtype == MACH_DS5000_200)
+		dec_kn02_be_init();
+	else
+		dec_kn03_be_init();
+
+	/* Clear any leftover errors from the firmware. */
+	dec_ecc_be_ack();
+}
diff -urN linux-2.4.21-bk33/arch/mips/dec/int-handler.S linux-2.4.21-bk34/arch/mips/dec/int-handler.S
--- linux-2.4.21-bk33/arch/mips/dec/int-handler.S	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/int-handler.S	2003-08-15 02:54:46.000000000 -0700
@@ -2,7 +2,7 @@
  * arch/mips/dec/int-handler.S
  *
  * Copyright (C) 1995, 1996, 1997 Paul M. Antoine and Harald Koerfgen
- * Copyright (C) 2000, 2001, 2002  Maciej W. Rozycki
+ * Copyright (C) 2000, 2001, 2002, 2003  Maciej W. Rozycki
  *
  * Written by Ralf Baechle and Andreas Busse, modified for DECStation
  * support by Paul Antoine and Harald Koerfgen.
@@ -132,19 +132,23 @@
 		 */
 		mfc0	t0,CP0_CAUSE		# get pending interrupts
 		mfc0	t1,CP0_STATUS
+#ifdef CONFIG_MIPS32
 		lw	t2,cpu_fpu_mask
+#endif
 		andi	t0,ST0_IM		# CAUSE.CE may be non-zero!
 		and	t0,t1			# isolate allowed ones
 
 		beqz	t0,spurious
 
+#ifdef CONFIG_MIPS32
 		 and	t2,t0
 		bnez	t2,fpu			# handle FPU immediately
+#endif
 
 		/*
 		 * Find irq with highest priority
 		 */
-		 la	t1,cpu_mask_nr_tbl
+		 PTR_LA	t1,cpu_mask_nr_tbl
 1:		lw	t2,(t1)
 		nop
 		and	t2,t0
@@ -161,14 +165,16 @@
 		 nop
 		jr	a0
 						# a trick to save a branch:
-		 lui	t2,KN03_IOASIC_BASE>>16	# upper part of IOASIC Address
+		 lui	t2,(KN03_IOASIC_BASE>>16)&0xffff
+						# upper part of IOASIC Address
 
 /*
  * Handle "IRQ Controller" Interrupts
  * Masked Interrupts are still visible and have to be masked "by hand".
  */
 		FEXPORT(kn02_io_int)		# 3max
-		lui	t0,KN02_CSR_ADDR>>16	# get interrupt status and mask
+		lui	t0,(KN02_CSR_BASE>>16)&0xffff
+						# get interrupt status and mask
 		lw	t0,(t0)
 		nop
 		andi	t1,t0,KN02_IRQ_ALL
@@ -176,11 +182,12 @@
 		 srl	t0,16			# shift interrupt mask
 
 		FEXPORT(kn02xa_io_int)		# 3min/maxine
-		lui	t2,KN02XA_IOASIC_BASE>>16 # upper part of IOASIC Address
+		lui	t2,(KN02XA_IOASIC_BASE>>16)&0xffff
+						# upper part of IOASIC Address
 
 		FEXPORT(kn03_io_int)		# 3max+ (t2 loaded earlier)
-		lw	t0,SIR(t2)		# get status: IOASIC isr
-		lw	t1,SIMR(t2)		# get mask:   IOASIC isrm
+		lw	t0,IO_REG_SIR(t2)	# get status: IOASIC sir
+		lw	t1,IO_REG_SIMR(t2)	# get mask:   IOASIC simr
 		nop
 
 1:		and	t0,t1			# mask out allowed ones
@@ -190,7 +197,7 @@
 		/*
 		 * Find irq with highest priority
 		 */
-		 la	t1,asic_mask_nr_tbl
+		 PTR_LA	t1,asic_mask_nr_tbl
 2:		lw	t2,(t1)
 		nop
 		and	t2,t0
@@ -263,9 +270,11 @@
 		j	ret_from_irq
 		 nop
 
+#ifdef CONFIG_MIPS32
 fpu:
 		j	handle_fpe_int
 		 nop
+#endif
 
 spurious:
 		j	spurious_interrupt
diff -urN linux-2.4.21-bk33/arch/mips/dec/ioasic-irq.c linux-2.4.21-bk34/arch/mips/dec/ioasic-irq.c
--- linux-2.4.21-bk33/arch/mips/dec/ioasic-irq.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/ioasic-irq.c	2003-08-15 02:54:46.000000000 -0700
@@ -3,7 +3,7 @@
  *
  *	DEC I/O ASIC interrupts.
  *
- *	Copyright (c) 2002  Maciej W. Rozycki
+ *	Copyright (c) 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -30,18 +30,18 @@
 {
 	u32 simr;
 
-	simr = ioasic_read(SIMR);
+	simr = ioasic_read(IO_REG_SIMR);
 	simr |= (1 << (irq - ioasic_irq_base));
-	ioasic_write(SIMR, simr);
+	ioasic_write(IO_REG_SIMR, simr);
 }
 
 static inline void mask_ioasic_irq(unsigned int irq)
 {
 	u32 simr;
 
-	simr = ioasic_read(SIMR);
+	simr = ioasic_read(IO_REG_SIMR);
 	simr &= ~(1 << (irq - ioasic_irq_base));
-	ioasic_write(SIMR, simr);
+	ioasic_write(IO_REG_SIMR, simr);
 }
 
 static inline void clear_ioasic_irq(unsigned int irq)
@@ -49,7 +49,7 @@
 	u32 sir;
 
 	sir = ~(1 << (irq - ioasic_irq_base));
-	ioasic_write(SIR, sir);
+	ioasic_write(IO_REG_SIR, sir);
 }
 
 static inline void enable_ioasic_irq(unsigned int irq)
@@ -93,17 +93,14 @@
 		enable_ioasic_irq(irq);
 }
 
-#define set_ioasic_affinity NULL
-
 static struct hw_interrupt_type ioasic_irq_type = {
-	"IO-ASIC",
-	startup_ioasic_irq,
-	shutdown_ioasic_irq,
-	enable_ioasic_irq,
-	disable_ioasic_irq,
-	ack_ioasic_irq,
-	end_ioasic_irq,
-	set_ioasic_affinity,
+	.typename = "IO-ASIC",
+	.startup = startup_ioasic_irq,
+	.shutdown = shutdown_ioasic_irq,
+	.enable = enable_ioasic_irq,
+	.disable = disable_ioasic_irq,
+	.ack = ack_ioasic_irq,
+	.end = end_ioasic_irq,
 };
 
 
@@ -124,17 +121,14 @@
 	end_ioasic_irq(irq);
 }
 
-#define set_ioasic_dma_affinity set_ioasic_affinity
-
 static struct hw_interrupt_type ioasic_dma_irq_type = {
-	"IO-ASIC-DMA",
-	startup_ioasic_dma_irq,
-	shutdown_ioasic_dma_irq,
-	enable_ioasic_dma_irq,
-	disable_ioasic_dma_irq,
-	ack_ioasic_dma_irq,
-	end_ioasic_dma_irq,
-	set_ioasic_dma_affinity,
+	.typename = "IO-ASIC-DMA",
+	.startup = startup_ioasic_dma_irq,
+	.shutdown = shutdown_ioasic_dma_irq,
+	.enable = enable_ioasic_dma_irq,
+	.disable = disable_ioasic_dma_irq,
+	.ack = ack_ioasic_dma_irq,
+	.end = end_ioasic_dma_irq,
 };
 
 
@@ -143,7 +137,7 @@
 	int i;
 
 	/* Mask interrupts. */
-	ioasic_write(SIMR, 0);
+	ioasic_write(IO_REG_SIMR, 0);
 	fast_iob();
 
 	for (i = base; i < base + IO_INR_DMA; i++) {
diff -urN linux-2.4.21-bk33/arch/mips/dec/kn02-irq.c linux-2.4.21-bk34/arch/mips/dec/kn02-irq.c
--- linux-2.4.21-bk33/arch/mips/dec/kn02-irq.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/kn02-irq.c	2003-08-15 02:54:46.000000000 -0700
@@ -4,7 +4,7 @@
  *	DECstation 5000/200 (KN02) Control and Status Register
  *	interrupts.
  *
- *	Copyright (c) 2002  Maciej W. Rozycki
+ *	Copyright (c) 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -37,7 +37,7 @@
 
 static inline void unmask_kn02_irq(unsigned int irq)
 {
-	volatile u32 *csr = (volatile u32 *)KN02_CSR_ADDR;
+	volatile u32 *csr = (volatile u32 *)KN02_CSR_BASE;
 
 	cached_kn02_csr |= (1 << (irq - kn02_irq_base + 16));
 	*csr = cached_kn02_csr;
@@ -45,7 +45,7 @@
 
 static inline void mask_kn02_irq(unsigned int irq)
 {
-	volatile u32 *csr = (volatile u32 *)KN02_CSR_ADDR;
+	volatile u32 *csr = (volatile u32 *)KN02_CSR_BASE;
 
 	cached_kn02_csr &= ~(1 << (irq - kn02_irq_base + 16));
 	*csr = cached_kn02_csr;
@@ -92,29 +92,29 @@
 		enable_kn02_irq(irq);
 }
 
-#define set_kn02_affinity NULL
-
 static struct hw_interrupt_type kn02_irq_type = {
-	"KN02-CSR",
-	startup_kn02_irq,
-	shutdown_kn02_irq,
-	enable_kn02_irq,
-	disable_kn02_irq,
-	ack_kn02_irq,
-	end_kn02_irq,
-	set_kn02_affinity,
+	.typename = "KN02-CSR",
+	.startup = startup_kn02_irq,
+	.shutdown = shutdown_kn02_irq,
+	.enable = enable_kn02_irq,
+	.disable = disable_kn02_irq,
+	.ack = ack_kn02_irq,
+	.end = end_kn02_irq,
 };
 
 
 void __init init_kn02_irqs(int base)
 {
-	volatile u32 *csr = (volatile u32 *)KN02_CSR_ADDR;
+	volatile u32 *csr = (volatile u32 *)KN02_CSR_BASE;
+	unsigned long flags;
 	int i;
 
-	/* Mask interrupts and preset write-only bits. */
-	cached_kn02_csr = (*csr & ~0xff0000) | 0xff;
+	/* Mask interrupts. */
+	spin_lock_irqsave(&kn02_lock, flags);
+	cached_kn02_csr &= ~KN03_CSR_IOINTEN;
 	*csr = cached_kn02_csr;
 	iob();
+	spin_unlock_irqrestore(&kn02_lock, flags);
 
 	for (i = base; i < base + KN02_IRQ_LINES; i++) {
 		irq_desc[i].status = IRQ_DISABLED;
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/Makefile linux-2.4.21-bk34/arch/mips/dec/prom/Makefile
--- linux-2.4.21-bk33/arch/mips/dec/prom/Makefile	2002-08-02 17:39:43.000000000 -0700
+++ linux-2.4.21-bk34/arch/mips/dec/prom/Makefile	2003-08-15 02:54:46.000000000 -0700
@@ -12,6 +12,9 @@
 
 L_TARGET  = rexlib.a
 
-obj-y +=  init.o memory.o cmdline.o identify.o locore.o
+obj-y			+= init.o memory.o cmdline.o identify.o
+
+obj-$(CONFIG_MIPS32)	+= locore.o
+obj-$(CONFIG_MIPS64)	+= call_o32.o
 
 include $(TOPDIR)/Rules.make
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/call_o32.S linux-2.4.21-bk34/arch/mips/dec/prom/call_o32.S
--- linux-2.4.21-bk33/arch/mips/dec/prom/call_o32.S	1969-12-31 16:00:00.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/prom/call_o32.S	2003-08-15 02:54:46.000000000 -0700
@@ -0,0 +1,91 @@
+/*
+ *	arch/mips/dec/call_o32.S
+ *
+ *	O32 interface for the 64 (or N32) ABI.
+ *
+ *	Copyright (C) 2002  Maciej W. Rozycki
+ *
+ *	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.
+ */
+
+#include <asm/asm.h>
+#include <asm/regdef.h>
+
+/* Maximum number of arguments supported.  Must be even!  */
+#define O32_ARGC	32
+/* Number of static registers we save.  */
+#define O32_STATC	11
+/* Frame size for both of the above.  */
+#define O32_FRAMESZ	(4 * O32_ARGC + SZREG * O32_STATC)
+
+		.text
+
+/*
+ * O32 function call dispatcher, for interfacing 32-bit ROM routines.
+ *
+ * The standard 64 (N32) calling sequence is supported, with a0
+ * holding a function pointer, a1-a7 -- its first seven arguments
+ * and the stack -- remaining ones (up to O32_ARGC, including a1-a7).
+ * Static registers, gp and fp are preserved, v0 holds a result.
+ * This code relies on the called o32 function for sp and ra
+ * restoration and thus both this dispatcher and the current stack
+ * have to be placed in a KSEGx (or KUSEG) address space.  Any
+ * pointers passed have to point to addresses within one of these
+ * spaces as well.
+ */
+NESTED(call_o32, O32_FRAMESZ, ra)
+		REG_SUBU	sp,O32_FRAMESZ
+
+		REG_S		ra,O32_FRAMESZ-1*SZREG(sp)
+		REG_S		fp,O32_FRAMESZ-2*SZREG(sp)
+		REG_S		gp,O32_FRAMESZ-3*SZREG(sp)
+		REG_S		s7,O32_FRAMESZ-4*SZREG(sp)
+		REG_S		s6,O32_FRAMESZ-5*SZREG(sp)
+		REG_S		s5,O32_FRAMESZ-6*SZREG(sp)
+		REG_S		s4,O32_FRAMESZ-7*SZREG(sp)
+		REG_S		s3,O32_FRAMESZ-8*SZREG(sp)
+		REG_S		s2,O32_FRAMESZ-9*SZREG(sp)
+		REG_S		s1,O32_FRAMESZ-10*SZREG(sp)
+		REG_S		s0,O32_FRAMESZ-11*SZREG(sp)
+
+		move		jp,a0
+
+		sll		a0,a1,zero
+		sll		a1,a2,zero
+		sll		a2,a3,zero
+		sll		a3,a4,zero
+		sw		a5,0x10(sp)
+		sw		a6,0x14(sp)
+		sw		a7,0x18(sp)
+
+		PTR_LA		t0,O32_FRAMESZ(sp)
+		PTR_LA		t1,0x1c(sp)
+		li		t2,O32_ARGC-7
+1:
+		lw		t3,(t0)
+		REG_ADDU	t0,SZREG
+		sw		t3,(t1)
+		REG_SUBU	t2,1
+		REG_ADDU	t1,4
+		bnez		t2,1b
+
+		jalr		jp
+
+		REG_L		s0,O32_FRAMESZ-11*SZREG(sp)
+		REG_L		s1,O32_FRAMESZ-10*SZREG(sp)
+		REG_L		s2,O32_FRAMESZ-9*SZREG(sp)
+		REG_L		s3,O32_FRAMESZ-8*SZREG(sp)
+		REG_L		s4,O32_FRAMESZ-7*SZREG(sp)
+		REG_L		s5,O32_FRAMESZ-6*SZREG(sp)
+		REG_L		s6,O32_FRAMESZ-5*SZREG(sp)
+		REG_L		s7,O32_FRAMESZ-4*SZREG(sp)
+		REG_L		gp,O32_FRAMESZ-3*SZREG(sp)
+		REG_L		fp,O32_FRAMESZ-2*SZREG(sp)
+		REG_L		ra,O32_FRAMESZ-1*SZREG(sp)
+
+		REG_ADDU	sp,O32_FRAMESZ
+		jr		ra
+END(call_o32)
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/cmdline.c linux-2.4.21-bk34/arch/mips/dec/prom/cmdline.c
--- linux-2.4.21-bk33/arch/mips/dec/prom/cmdline.c	2002-08-02 17:39:43.000000000 -0700
+++ linux-2.4.21-bk34/arch/mips/dec/prom/cmdline.c	2003-08-15 02:54:46.000000000 -0700
@@ -6,32 +6,30 @@
 #include <linux/init.h>
 #include <linux/kernel.h>
 #include <linux/string.h>
+#include <linux/types.h>
 
 #include <asm/bootinfo.h>
-
-#include "prom.h"
+#include <asm/dec/prom.h>
 
 #undef PROM_DEBUG
 
-#ifdef PROM_DEBUG
-extern int (*prom_printf)(char *, ...);
-#endif
-
 char arcs_cmdline[CL_SIZE];
 
-void __init prom_init_cmdline(int argc, char **argv, unsigned long magic)
+void __init prom_init_cmdline(s32 argc, s32 *argv, u32 magic)
 {
+	char *arg;
 	int start_arg, i;
 
 	/*
 	 * collect args and prepare cmd_line
 	 */
-	if (magic != REX_PROM_MAGIC)
+	if (!prom_is_rex(magic))
 		start_arg = 1;
 	else
 		start_arg = 2;
 	for (i = start_arg; i < argc; i++) {
-		strcat(arcs_cmdline, argv[i]);
+		arg = (void *)(long)(argv[i]);
+		strcat(arcs_cmdline, arg);
 		if (i < (argc - 1))
 			strcat(arcs_cmdline, " ");
 	}
@@ -39,6 +37,4 @@
 #ifdef PROM_DEBUG
 	prom_printf("arcs_cmdline: %s\n", &(arcs_cmdline[0]));
 #endif
-
 }
-
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/identify.c linux-2.4.21-bk34/arch/mips/dec/prom/identify.c
--- linux-2.4.21-bk33/arch/mips/dec/prom/identify.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/prom/identify.c	2003-08-15 02:54:46.000000000 -0700
@@ -2,50 +2,104 @@
  * identify.c: machine identification code.
  *
  * Copyright (C) 1998 Harald Koerfgen and Paul M. Antoine
+ * Copyright (C) 2002, 2003  Maciej W. Rozycki
  */
 #include <linux/init.h>
 #include <linux/kernel.h>
+#include <linux/mc146818rtc.h>
 #include <linux/string.h>
+#include <linux/types.h>
 
 #include <asm/bootinfo.h>
+#include <asm/dec/ioasic.h>
+#include <asm/dec/ioasic_addrs.h>
+#include <asm/dec/kn01.h>
+#include <asm/dec/kn02.h>
+#include <asm/dec/kn02ba.h>
+#include <asm/dec/kn02ca.h>
+#include <asm/dec/kn03.h>
+#include <asm/dec/kn230.h>
+#include <asm/dec/prom.h>
 
 #include "dectypes.h"
-#include "prom.h"
-
-extern char *(*prom_getenv)(char *);
-extern int (*prom_printf)(char *, ...);
-extern int (*rex_getsysid)(void);
 
 extern unsigned long mips_machgroup;
 extern unsigned long mips_machtype;
 
-extern unsigned long mips_machtype;
+static const char *dec_system_strings[] = {
+	[MACH_DSUNKNOWN]	"unknown DECstation",
+	[MACH_DS23100]		"DECstation 2100/3100",
+	[MACH_DS5100]		"DECsystem 5100",
+	[MACH_DS5000_200]	"DECstation 5000/200",
+	[MACH_DS5000_1XX]	"DECstation 5000/1xx",
+	[MACH_DS5000_XX]	"Personal DECstation 5000/xx",
+	[MACH_DS5000_2X0]	"DECstation 5000/2x0",
+	[MACH_DS5400]		"DECsystem 5400",
+	[MACH_DS5500]		"DECsystem 5500",
+	[MACH_DS5800]		"DECsystem 5800",
+	[MACH_DS5900]		"DECsystem 5900",
+};
+
 const char *get_system_type(void)
 {
-	static char system[32];
-	int called = 0;
-	const char *dec_system_strings[] = { "unknown", "DECstation 2100/3100",
-        	"DECstation 5100", "DECstation 5000/200", "DECstation 5000/1xx",
-		"Personal DECstation 5000/xx", "DECstation 5000/2x0",
-		"DECstation 5400", "DECstation 5500", "DECstation 5800"
-	};
+#define STR_BUF_LEN	64
+	static char system[STR_BUF_LEN];
+	static int called = 0;
 
 	if (called == 0) {
 		called = 1;
-		strcpy(system, "Digital ");
-		strcat(system, dec_system_strings[mips_machtype]);
+		snprintf(system, STR_BUF_LEN, "Digital %s",
+			 dec_system_strings[mips_machtype]);
 	}
 
 	return system;
 }
 
-void __init prom_identify_arch (unsigned int magic)
+
+/*
+ * Setup essential system-specific memory addresses.  We need them
+ * early.  Semantically the functions belong to prom/init.c, but they
+ * are compact enough we want them inlined. --macro
+ */
+static inline void prom_init_kn01(void)
 {
-	unsigned char dec_cpunum, dec_firmrev, dec_etc;
-	int dec_systype;
-	unsigned long dec_sysid;
+	dec_rtc_base = (void *)KN01_RTC_BASE;
+	dec_kn_slot_size = KN01_SLOT_SIZE;
+}
 
-	if (magic != REX_PROM_MAGIC) {
+static inline void prom_init_kn230(void)
+{
+	dec_rtc_base = (void *)KN01_RTC_BASE;
+	dec_kn_slot_size = KN01_SLOT_SIZE;
+}
+
+static inline void prom_init_kn02(void)
+{
+	dec_rtc_base = (void *)KN02_RTC_BASE;
+	dec_kn_slot_size = KN02_SLOT_SIZE;
+}
+
+static inline void prom_init_kn02xa(void)
+{
+	ioasic_base = (void *)KN02XA_IOASIC_BASE;
+	dec_rtc_base = (void *)KN02XA_RTC_BASE;
+	dec_kn_slot_size = IOASIC_SLOT_SIZE;
+}
+
+static inline void prom_init_kn03(void)
+{
+	ioasic_base = (void *)KN03_IOASIC_BASE;
+	dec_rtc_base = (void *)KN03_RTC_BASE;
+	dec_kn_slot_size = IOASIC_SLOT_SIZE;
+}
+
+
+void __init prom_identify_arch(u32 magic)
+{
+	unsigned char dec_cpunum, dec_firmrev, dec_etc, dec_systype;
+	u32 dec_sysid;
+
+	if (!prom_is_rex(magic)) {
 		dec_sysid = simple_strtoul(prom_getenv("systype"), (char **)0, 0);
 	} else {
 		dec_sysid = rex_getsysid();
@@ -67,50 +121,52 @@
 	 * FIXME: This may not be an exhaustive list of DECStations/Servers!
 	 * Put all model-specific initialisation calls here.
 	 */
-	prom_printf("This DECstation is a ");
-
 	switch (dec_systype) {
 	case DS2100_3100:
-		prom_printf("DS2100/3100\n");
 		mips_machtype = MACH_DS23100;
+		prom_init_kn01();
 		break;
 	case DS5100:		/* DS5100 MIPSMATE */
-		prom_printf("DS5100\n");
 		mips_machtype = MACH_DS5100;
+		prom_init_kn230();
 		break;
 	case DS5000_200:	/* DS5000 3max */
-		prom_printf("DS5000/200\n");
 		mips_machtype = MACH_DS5000_200;
+		prom_init_kn02();
 		break;
 	case DS5000_1XX:	/* DS5000/100 3min */
-		prom_printf("DS5000/1xx\n");
 		mips_machtype = MACH_DS5000_1XX;
+		prom_init_kn02xa();
 		break;
-	case DS5000_2X0:	/* DS5000/240 3max+ */
-		prom_printf("DS5000/2x0\n");
+	case DS5000_2X0:	/* DS5000/240 3max+ or DS5900 bigmax */
 		mips_machtype = MACH_DS5000_2X0;
+		prom_init_kn03();
+		if (!(ioasic_read(IO_REG_SIR) & KN03_IO_INR_3MAXP))
+			mips_machtype = MACH_DS5900;
 		break;
-	case DS5000_XX:	/* Personal DS5000/2x */
-		prom_printf("Personal DS5000/xx\n");
+	case DS5000_XX:		/* Personal DS5000/xx maxine */
 		mips_machtype = MACH_DS5000_XX;
+		prom_init_kn02xa();
 		break;
 	case DS5800:		/* DS5800 Isis */
-		prom_printf("DS5800\n");
 		mips_machtype = MACH_DS5800;
 		break;
 	case DS5400:		/* DS5400 MIPSfair */
-		prom_printf("DS5400\n");
 		mips_machtype = MACH_DS5400;
 		break;
 	case DS5500:		/* DS5500 MIPSfair-2 */
-		prom_printf("DS5500\n");
 		mips_machtype = MACH_DS5500;
 		break;
 	default:
-		prom_printf("unknown, id is %x", dec_systype);
 		mips_machtype = MACH_DSUNKNOWN;
 		break;
 	}
-}
-
 
+	if (mips_machtype == MACH_DSUNKNOWN)
+		prom_printf("This is an %s, id is %x\n",
+			    dec_system_strings[mips_machtype],
+			    dec_systype);
+	else
+		prom_printf("This is a %s\n",
+			    dec_system_strings[mips_machtype]);
+}
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/init.c linux-2.4.21-bk34/arch/mips/dec/prom/init.c
--- linux-2.4.21-bk33/arch/mips/dec/prom/init.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/prom/init.c	2003-08-15 02:54:46.000000000 -0700
@@ -2,98 +2,102 @@
  * init.c: PROM library initialisation code.
  *
  * Copyright (C) 1998 Harald Koerfgen
+ * Copyright (C) 2002  Maciej W. Rozycki
  */
-#include <linux/init.h>
 #include <linux/config.h>
+#include <linux/init.h>
+#include <linux/types.h>
+
 #include <asm/bootinfo.h>
 #include <asm/cpu.h>
-#include "prom.h"
+#include <asm/processor.h>
+
+#include <asm/dec/prom.h>
+
+
+int (*__rex_bootinit)(void);
+int (*__rex_bootread)(void);
+int (*__rex_getbitmap)(memmap *);
+unsigned long *(*__rex_slot_address)(int);
+void *(*__rex_gettcinfo)(void);
+int (*__rex_getsysid)(void);
+void (*__rex_clear_cache)(void);
+
+int (*__prom_getchar)(void);
+char *(*__prom_getenv)(char *);
+int (*__prom_printf)(char *, ...);
+
+int (*__pmax_open)(char*, int);
+int (*__pmax_lseek)(int, long, int);
+int (*__pmax_read)(int, void *, int);
+int (*__pmax_close)(int);
 
-/*
- * PROM Interface (whichprom.c)
- */
-typedef struct {
-	int pagesize;
-	unsigned char bitmap[0];
-} memmap;
-
-int (*rex_bootinit)(void);
-int (*rex_bootread)(void);
-int (*rex_getbitmap)(memmap *);
-unsigned long *(*rex_slot_address)(int);
-void *(*rex_gettcinfo)(void);
-int (*rex_getsysid)(void);
-void (*rex_clear_cache)(void);
-
-int (*prom_getchar)(void);
-char *(*prom_getenv)(char *);
-int (*prom_printf)(char *, ...);
-
-int (*pmax_open)(char*, int);
-int (*pmax_lseek)(int, long, int);
-int (*pmax_read)(int, void *, int);
-int (*pmax_close)(int);
-
-extern void prom_meminit(unsigned int);
-extern void prom_identify_arch(unsigned int);
-extern void prom_init_cmdline(int, char **, unsigned long);
 
 /*
  * Detect which PROM's the DECSTATION has, and set the callback vectors
  * appropriately.
  */
-void __init which_prom(unsigned long magic, int *prom_vec)
+void __init which_prom(s32 magic, s32 *prom_vec)
 {
 	/*
 	 * No sign of the REX PROM's magic number means we assume a non-REX
 	 * machine (i.e. we're on a DS2100/3100, DS5100 or DS5000/2xx)
 	 */
-	if (magic == REX_PROM_MAGIC)
-	{
+	if (prom_is_rex(magic)) {
 		/*
 		 * Set up prom abstraction structure with REX entry points.
 		 */
-		rex_bootinit = (int (*)(void)) *(prom_vec + REX_PROM_BOOTINIT);
-		rex_bootread = (int (*)(void)) *(prom_vec + REX_PROM_BOOTREAD);
-		rex_getbitmap = (int (*)(memmap *)) *(prom_vec + REX_PROM_GETBITMAP);
-		prom_getchar = (int (*)(void)) *(prom_vec + REX_PROM_GETCHAR);
-		prom_getenv = (char *(*)(char *)) *(prom_vec + REX_PROM_GETENV);
-		rex_getsysid = (int (*)(void)) *(prom_vec + REX_PROM_GETSYSID);
-		rex_gettcinfo = (void *(*)(void)) *(prom_vec + REX_PROM_GETTCINFO);
-		prom_printf = (int (*)(char *, ...)) *(prom_vec + REX_PROM_PRINTF);
-		rex_slot_address = (unsigned long *(*)(int)) *(prom_vec + REX_PROM_SLOTADDR);
-		rex_clear_cache = (void (*)(void)) * (prom_vec + REX_PROM_CLEARCACHE);
-	}
-	else
-	{
+		__rex_bootinit =
+			(void *)(long)*(prom_vec + REX_PROM_BOOTINIT);
+		__rex_bootread =
+			(void *)(long)*(prom_vec + REX_PROM_BOOTREAD);
+		__rex_getbitmap =
+			(void *)(long)*(prom_vec + REX_PROM_GETBITMAP);
+		__prom_getchar =
+			(void *)(long)*(prom_vec + REX_PROM_GETCHAR);
+		__prom_getenv =
+			(void *)(long)*(prom_vec + REX_PROM_GETENV);
+		__rex_getsysid =
+			(void *)(long)*(prom_vec + REX_PROM_GETSYSID);
+		__rex_gettcinfo =
+			(void *)(long)*(prom_vec + REX_PROM_GETTCINFO);
+		__prom_printf =
+			(void *)(long)*(prom_vec + REX_PROM_PRINTF);
+		__rex_slot_address =
+			(void *)(long)*(prom_vec + REX_PROM_SLOTADDR);
+		__rex_clear_cache =
+			(void *)(long)*(prom_vec + REX_PROM_CLEARCACHE);
+	} else {
 		/*
 		 * Set up prom abstraction structure with non-REX entry points.
 		 */
-		prom_getchar = (int (*)(void)) PMAX_PROM_GETCHAR;
-		prom_getenv = (char *(*)(char *)) PMAX_PROM_GETENV;
-		prom_printf = (int (*)(char *, ...)) PMAX_PROM_PRINTF;
-		pmax_open = (int (*)(char *, int)) PMAX_PROM_OPEN;
-		pmax_lseek = (int (*)(int, long, int)) PMAX_PROM_LSEEK;
-		pmax_read = (int (*)(int, void *, int)) PMAX_PROM_READ;
-		pmax_close = (int (*)(int)) PMAX_PROM_CLOSE;
+		__prom_getchar = (void *)PMAX_PROM_GETCHAR;
+		__prom_getenv = (void *)PMAX_PROM_GETENV;
+		__prom_printf = (void *)PMAX_PROM_PRINTF;
+		__pmax_open = (void *)PMAX_PROM_OPEN;
+		__pmax_lseek = (void *)PMAX_PROM_LSEEK;
+		__pmax_read = (void *)PMAX_PROM_READ;
+		__pmax_close = (void *)PMAX_PROM_CLOSE;
 	}
 }
 
-int __init prom_init(int argc, char **argv,
-	       unsigned long magic, int *prom_vec)
+int __init prom_init(s32 argc, s32 *argv, u32 magic, s32 *prom_vec)
 {
 	extern void dec_machine_halt(void);
 
-	/* Determine which PROM's we have (and therefore which machine we're on!) */
+	/*
+	 * Determine which PROM's we have
+	 * (and therefore which machine we're on!)
+	 */
 	which_prom(magic, prom_vec);
 
-	if (magic == REX_PROM_MAGIC)
+	if (prom_is_rex(magic))
 		rex_clear_cache();
 
 	/* Were we compiled with the right CPU option? */
 #if defined(CONFIG_CPU_R3000)
-	if ((mips_cpu.cputype == CPU_R4000SC) ||
-	    (mips_cpu.cputype == CPU_R4400SC)) {
+	if ((current_cpu_data.cputype == CPU_R4000SC) ||
+	    (current_cpu_data.cputype == CPU_R4400SC)) {
 		prom_printf("Sorry, this kernel is compiled for the wrong CPU type!\n");
 		prom_printf("Please recompile with \"CONFIG_CPU_R4x00 = y\"\n");
 		dec_machine_halt();
@@ -101,8 +105,8 @@
 #endif
 
 #if defined(CONFIG_CPU_R4X00)
-	if ((mips_cpu.cputype == CPU_R3000) ||
-	    (mips_cpu.cputype == CPU_R3000A)) {
+	if ((current_cpu_data.cputype == CPU_R3000) ||
+	    (current_cpu_data.cputype == CPU_R3000A)) {
 		prom_printf("Sorry, this kernel is compiled for the wrong CPU type!\n");
 		prom_printf("Please recompile with \"CONFIG_CPU_R3000 = y\"\n");
 		dec_machine_halt();
@@ -115,4 +119,3 @@
 
 	return 0;
 }
-
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/locore.S linux-2.4.21-bk34/arch/mips/dec/prom/locore.S
--- linux-2.4.21-bk33/arch/mips/dec/prom/locore.S	1999-06-25 17:40:12.000000000 -0700
+++ linux-2.4.21-bk34/arch/mips/dec/prom/locore.S	2003-08-15 02:54:46.000000000 -0700
@@ -19,11 +19,11 @@
 	mfc0	k0, CP0_STATUS
 	la	k1, mem_err
 
-	sw	k0,0(k1)
+	sw	k0, 0(k1)
 
 	mfc0	k0, CP0_EPC
 	nop
-	addiu	k0,4		# skip the causing instruction
+	addiu	k0, 4		# skip the causing instruction
 	jr	k0
 	 rfe
 END(genexcept_early)
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/memory.c linux-2.4.21-bk34/arch/mips/dec/prom/memory.c
--- linux-2.4.21-bk33/arch/mips/dec/prom/memory.c	2002-08-02 17:39:43.000000000 -0700
+++ linux-2.4.21-bk34/arch/mips/dec/prom/memory.c	2003-08-15 02:54:46.000000000 -0700
@@ -2,35 +2,21 @@
  * memory.c: memory initialisation code.
  *
  * Copyright (C) 1998 Harald Koerfgen, Frieder Streffer and Paul M. Antoine
- * Copyright (C) 2000 Maciej W. Rozycki
+ * Copyright (C) 2000, 2002  Maciej W. Rozycki
  */
-#include <linux/init.h>
 #include <linux/config.h>
+#include <linux/init.h>
 #include <linux/kernel.h>
 #include <linux/mm.h>
 #include <linux/bootmem.h>
+#include <linux/types.h>
 
 #include <asm/addrspace.h>
-#include <asm/page.h>
-
 #include <asm/bootinfo.h>
-
 #include <asm/dec/machtype.h>
+#include <asm/dec/prom.h>
+#include <asm/page.h>
 
-#include "prom.h"
-
-typedef struct {
-	int pagesize;
-	unsigned char bitmap[0];
-} memmap;
-
-extern int (*rex_getbitmap)(memmap *);
-
-#undef PROM_DEBUG
-
-#ifdef PROM_DEBUG
-extern int (*prom_printf)(char *, ...);
-#endif
 
 volatile unsigned long mem_err = 0;	/* So we know an error occurred */
 
@@ -41,10 +27,10 @@
 
 #define CHUNK_SIZE 0x400000
 
-static void __init pmax_setup_memory_region(void)
+static inline void pmax_setup_memory_region(void)
 {
 	volatile unsigned char *memory_page, dummy;
-	char	old_handler[0x80];
+	char old_handler[0x80];
 	extern char genexcept_early;
 
 	/* Install exception handler */
@@ -71,14 +57,14 @@
  * Use the REX prom calls to get hold of the memory bitmap, and thence
  * determine memory size.
  */
-static void __init rex_setup_memory_region(void)
+static inline void rex_setup_memory_region(void)
 {
 	int i, bitmap_size;
 	unsigned long mem_start = 0, mem_size = 0;
 	memmap *bm;
 
 	/* some free 64k */
-	bm = (memmap *) 0x80028000;
+	bm = (memmap *)KSEG0ADDR(0x28000);
 
 	bitmap_size = rex_getbitmap(bm);
 
@@ -98,9 +84,9 @@
 		add_memory_region(mem_start, mem_size, BOOT_MEM_RAM);
 }
 
-void __init prom_meminit(unsigned int magic)
+void __init prom_meminit(u32 magic)
 {
-	if (magic != REX_PROM_MAGIC)
+	if (!prom_is_rex(magic))
 		pmax_setup_memory_region();
 	else
 		rex_setup_memory_region();
diff -urN linux-2.4.21-bk33/arch/mips/dec/prom/prom.h linux-2.4.21-bk34/arch/mips/dec/prom/prom.h
--- linux-2.4.21-bk33/arch/mips/dec/prom/prom.h	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/prom/prom.h	1969-12-31 16:00:00.000000000 -0800
@@ -1,51 +0,0 @@
-/*
- * Miscellaneous definitions used to call the routines contained in the boot
- * PROMs on various models of DECSTATION's.
- * the rights to redistribute these changes.
- */
-
-#ifndef __ASM_DEC_PROM_H
-#define __ASM_DEC_PROM_H
-
-/*
- * PMAX/3MAX PROM entry points for DS2100/3100's and DS5000/2xx's.  Many of
- * these will work for MIPSen as well!
- */
-#define VEC_RESET		0xBFC00000		/* Prom base address */
-#define	PMAX_PROM_ENTRY(x)	(VEC_RESET+((x)*8))	/* Prom jump table */
-
-#define	PMAX_PROM_HALT		PMAX_PROM_ENTRY(2)	/* valid on MIPSen */
-#define	PMAX_PROM_AUTOBOOT	PMAX_PROM_ENTRY(5)	/* valid on MIPSen */
-#define	PMAX_PROM_OPEN		PMAX_PROM_ENTRY(6)
-#define	PMAX_PROM_READ		PMAX_PROM_ENTRY(7)
-#define	PMAX_PROM_CLOSE		PMAX_PROM_ENTRY(10)
-#define	PMAX_PROM_LSEEK		PMAX_PROM_ENTRY(11)
-#define PMAX_PROM_GETCHAR       PMAX_PROM_ENTRY(12)
-#define	PMAX_PROM_PUTCHAR	PMAX_PROM_ENTRY(13)	/* 12 on MIPSen */
-#define	PMAX_PROM_GETS		PMAX_PROM_ENTRY(15)
-#define	PMAX_PROM_PRINTF	PMAX_PROM_ENTRY(17)
-#define	PMAX_PROM_GETENV	PMAX_PROM_ENTRY(33)	/* valid on MIPSen */
-
-/*
- * Magic number indicating REX PROM available on DECSTATION.  Found in
- * register a2 on transfer of control to program from PROM.
- */
-#define	REX_PROM_MAGIC		0x30464354
-
-/*
- * 3MIN/MAXINE PROM entry points for DS5000/1xx's, DS5000/xx's, and
- * DS5000/2x0.
- */
-#define REX_PROM_GETBITMAP	0x84/4	/* get mem bitmap */
-#define REX_PROM_GETCHAR	0x24/4	/* getch() */
-#define REX_PROM_GETENV		0x64/4	/* get env. variable */
-#define REX_PROM_GETSYSID	0x80/4	/* get system id */
-#define REX_PROM_GETTCINFO	0xa4/4
-#define REX_PROM_PRINTF		0x30/4	/* printf() */
-#define REX_PROM_SLOTADDR	0x6c/4	/* slotaddr */
-#define REX_PROM_BOOTINIT	0x54/4	/* open() */
-#define REX_PROM_BOOTREAD	0x58/4	/* read() */
-#define REX_PROM_CLEARCACHE	0x7c/4
-
-#endif /* __ASM_DEC_PROM_H */
-
diff -urN linux-2.4.21-bk33/arch/mips/dec/promcon.c linux-2.4.21-bk34/arch/mips/dec/promcon.c
--- linux-2.4.21-bk33/arch/mips/dec/promcon.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/promcon.c	2003-08-15 02:54:46.000000000 -0700
@@ -12,8 +12,7 @@
 #include <linux/console.h>
 #include <linux/fs.h>
 
-extern int (*prom_getchar) (void);
-extern int (*prom_printf) (char *,...);
+#include <asm/dec/prom.h>
 
 static void prom_console_write(struct console *co, const char *s,
 			       unsigned count)
@@ -42,12 +41,12 @@
 
 static struct console sercons =
 {
-    name:	"ttyS",
-    write:	prom_console_write,
-    device:	prom_console_device,
-    setup:	prom_console_setup,
-    flags:	CON_PRINTBUFFER,
-    index:	-1,
+    .name	= "ttyS",
+    .write	= prom_console_write,
+    .device	= prom_console_device,
+    .setup	= prom_console_setup,
+    .flags	= CON_PRINTBUFFER,
+    .index	= -1,
 };
 
 /*
diff -urN linux-2.4.21-bk33/arch/mips/dec/reset.c linux-2.4.21-bk34/arch/mips/dec/reset.c
--- linux-2.4.21-bk33/arch/mips/dec/reset.c	2002-08-02 17:39:43.000000000 -0700
+++ linux-2.4.21-bk34/arch/mips/dec/reset.c	2003-08-15 02:54:46.000000000 -0700
@@ -1,8 +1,14 @@
 /*
  * Reset a DECstation machine.
+ *
+ * Copyright (C) 199x  the Anonymous
+ * Copyright (C) 2001, 2002, 2003  Maciej W. Rozycki
  */
 
-void (*back_to_prom)(void) = (void (*)(void))0xBFC00000;
+#include <asm/addrspace.h>
+#include <asm/ptrace.h>
+
+#define back_to_prom()	(((void (*)(void))KSEG1ADDR(0x1fc00000))())
 
 void dec_machine_restart(char *command)
 {
diff -urN linux-2.4.21-bk33/arch/mips/dec/rtc-dec.c linux-2.4.21-bk34/arch/mips/dec/rtc-dec.c
--- linux-2.4.21-bk33/arch/mips/dec/rtc-dec.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/rtc-dec.c	2003-08-15 02:54:46.000000000 -0700
@@ -11,6 +11,7 @@
  */
 
 #include <linux/mc146818rtc.h>
+#include <linux/module.h>
 #include <linux/types.h>
 
 volatile u8 *dec_rtc_base;
@@ -35,3 +36,5 @@
 	&dec_rtc_write_data,
 	&dec_rtc_bcd_mode
 };
+
+EXPORT_SYMBOL(dec_rtc_base);
diff -urN linux-2.4.21-bk33/arch/mips/dec/setup.c linux-2.4.21-bk34/arch/mips/dec/setup.c
--- linux-2.4.21-bk33/arch/mips/dec/setup.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/setup.c	2003-08-15 02:54:46.000000000 -0700
@@ -6,7 +6,7 @@
  * for more details.
  *
  * Copyright (C) 1998 Harald Koerfgen
- * Copyright (C) 2000, 2001, 2002  Maciej W. Rozycki
+ * Copyright (C) 2000, 2001, 2002, 2003  Maciej W. Rozycki
  */
 #include <linux/config.h>
 #include <linux/sched.h>
@@ -16,6 +16,7 @@
 #include <linux/console.h>
 #include <linux/init.h>
 #include <linux/module.h>
+#include <linux/spinlock.h>
 #include <linux/types.h>
 
 #include <asm/cpu.h>
@@ -24,19 +25,20 @@
 #include <asm/irq_cpu.h>
 #include <asm/mipsregs.h>
 #include <asm/reboot.h>
+#include <asm/time.h>
 #include <asm/traps.h>
 #include <asm/wbflush.h>
 
 #include <asm/dec/interrupts.h>
+#include <asm/dec/ioasic.h>
+#include <asm/dec/ioasic_addrs.h>
+#include <asm/dec/ioasic_ints.h>
 #include <asm/dec/kn01.h>
 #include <asm/dec/kn02.h>
 #include <asm/dec/kn02ba.h>
 #include <asm/dec/kn02ca.h>
 #include <asm/dec/kn03.h>
 #include <asm/dec/kn230.h>
-#include <asm/dec/ioasic.h>
-#include <asm/dec/ioasic_addrs.h>
-#include <asm/dec/ioasic_ints.h>
 
 
 extern void dec_machine_restart(char *command);
@@ -46,6 +48,8 @@
 
 extern asmlinkage void decstation_handle_int(void);
 
+spinlock_t ioasic_ssr_lock;
+
 volatile u32 *ioasic_base;
 unsigned long dec_kn_slot_size;
 
@@ -75,53 +79,61 @@
 	[0 ... DEC_NR_INTS - 1] = -1
 };
 int_ptr cpu_mask_nr_tbl[DEC_MAX_CPU_INTS][2] = {
-	{ { i: ~0 }, { p: dec_intr_unimplemented } },
+	{ { .i = ~0 }, { .p = dec_intr_unimplemented } },
 };
 int_ptr asic_mask_nr_tbl[DEC_MAX_ASIC_INTS][2] = {
-	{ { i: ~0 }, { p: asic_intr_unimplemented } },
+	{ { .i = ~0 }, { .p = asic_intr_unimplemented } },
 };
 int cpu_fpu_mask = DEC_CPU_IRQ_MASK(DEC_CPU_INR_FPU);
 
-static struct irqaction ioirq = {NULL, 0, 0, "cascade", NULL, NULL};
-static struct irqaction fpuirq = {NULL, 0, 0, "fpu", NULL, NULL};
-
-static struct irqaction haltirq = {dec_intr_halt, 0, 0, "halt", NULL, NULL};
+static struct irqaction ioirq = {
+	.handler = no_action,
+	.name = "cascade",
+};
+static struct irqaction fpuirq = {
+	.handler = no_action,
+	.name = "fpu",
+};
 
+static struct irqaction busirq = {
+	.flags = SA_INTERRUPT,
+	.name = "bus error",
+};
 
-void (*board_time_init) (struct irqaction * irq);
+static struct irqaction haltirq = {
+	.handler = dec_intr_halt,
+	.name = "halt",
+};
 
 
 /*
- * enable the periodic interrupts
+ * Bus error (DBE/IBE exceptions and bus interrupts) handling setup.
  */
-static void __init dec_time_init(struct irqaction *irq)
+void __init dec_be_init(void)
 {
-	/*
-	* Here we go, enable periodic rtc interrupts.
-	*/
-
-#ifndef LOG_2_HZ
-#  define LOG_2_HZ 7
-#endif
-
-	CMOS_WRITE(RTC_REF_CLCK_32KHZ | (16 - LOG_2_HZ), RTC_REG_A);
-	CMOS_WRITE(CMOS_READ(RTC_REG_B) | RTC_PIE, RTC_REG_B);
-	setup_irq(dec_interrupt[DEC_IRQ_RTC], irq);
+	switch (mips_machtype) {
+	case MACH_DS23100:	/* DS2100/DS3100 Pmin/Pmax */
+		busirq.flags |= SA_SHIRQ;
+		break;
+	case MACH_DS5000_200:	/* DS5000/200 3max */
+	case MACH_DS5000_2X0:	/* DS5000/240 3max+ */
+	case MACH_DS5900:	/* DS5900 bigmax */
+		board_be_handler = dec_ecc_be_handler;
+		busirq.handler = dec_ecc_be_interrupt;
+		dec_ecc_be_init();
+		break;
+	}
 }
 
 
-/*
- * Bus error (DBE/IBE exceptions and memory interrupts) handling
- * setup.  Nothing for now.
- */
-void __init bus_error_init(void)
-{
-}
-
+extern void dec_time_init(void);
+extern void dec_timer_setup(struct irqaction *);
 
 void __init decstation_setup(void)
 {
+	board_be_init = dec_be_init;
 	board_time_init = dec_time_init;
+	board_timer_setup = dec_timer_setup;
 
 	wbflush_setup();
 
@@ -152,7 +164,7 @@
 	[DEC_IRQ_HALT]		= -1,
 	[DEC_IRQ_ISDN]		= -1,
 	[DEC_IRQ_LANCE]		= DEC_CPU_IRQ_NR(KN01_CPU_INR_LANCE),
-	[DEC_IRQ_MEMORY]	= DEC_CPU_IRQ_NR(KN01_CPU_INR_MEMORY),
+	[DEC_IRQ_BUS]		= DEC_CPU_IRQ_NR(KN01_CPU_INR_BUS),
 	[DEC_IRQ_PSU]		= -1,
 	[DEC_IRQ_RTC]		= DEC_CPU_IRQ_NR(KN01_CPU_INR_RTC),
 	[DEC_IRQ_SCC0]		= -1,
@@ -175,10 +187,10 @@
 	[DEC_IRQ_SCC0A_RXDMA]	= -1,
 	[DEC_IRQ_SCC0A_TXERR]	= -1,
 	[DEC_IRQ_SCC0A_TXDMA]	= -1,
-	[DEC_IRQ_SCC0B_RXERR]	= -1,
-	[DEC_IRQ_SCC0B_RXDMA]	= -1,
-	[DEC_IRQ_SCC0B_TXERR]	= -1,
-	[DEC_IRQ_SCC0B_TXDMA]	= -1,
+	[DEC_IRQ_AB_RXERR]	= -1,
+	[DEC_IRQ_AB_RXDMA]	= -1,
+	[DEC_IRQ_AB_TXERR]	= -1,
+	[DEC_IRQ_AB_TXDMA]	= -1,
 	[DEC_IRQ_SCC1A_RXERR]	= -1,
 	[DEC_IRQ_SCC1A_RXDMA]	= -1,
 	[DEC_IRQ_SCC1A_TXERR]	= -1,
@@ -186,26 +198,22 @@
 };
 
 static int_ptr kn01_cpu_mask_nr_tbl[][2] __initdata = {
-	{ { i: DEC_CPU_IRQ_MASK(KN01_CPU_INR_MEMORY) },
-		{ i: DEC_CPU_IRQ_NR(KN01_CPU_INR_MEMORY) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN01_CPU_INR_RTC) },
-		{ i: DEC_CPU_IRQ_NR(KN01_CPU_INR_RTC) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN01_CPU_INR_DZ11) },
-		{ i: DEC_CPU_IRQ_NR(KN01_CPU_INR_DZ11) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN01_CPU_INR_SII) },
-		{ i: DEC_CPU_IRQ_NR(KN01_CPU_INR_SII) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN01_CPU_INR_LANCE) },
-		{ i: DEC_CPU_IRQ_NR(KN01_CPU_INR_LANCE) } },
-	{ { i: DEC_CPU_IRQ_ALL },
-		{ p: cpu_all_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN01_CPU_INR_BUS) },
+		{ .i = DEC_CPU_IRQ_NR(KN01_CPU_INR_BUS) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN01_CPU_INR_RTC) },
+		{ .i = DEC_CPU_IRQ_NR(KN01_CPU_INR_RTC) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN01_CPU_INR_DZ11) },
+		{ .i = DEC_CPU_IRQ_NR(KN01_CPU_INR_DZ11) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN01_CPU_INR_SII) },
+		{ .i = DEC_CPU_IRQ_NR(KN01_CPU_INR_SII) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN01_CPU_INR_LANCE) },
+		{ .i = DEC_CPU_IRQ_NR(KN01_CPU_INR_LANCE) } },
+	{ { .i = DEC_CPU_IRQ_ALL },
+		{ .p = cpu_all_int } },
 };
 
 void __init dec_init_kn01(void)
 {
-	/* Setup some memory addresses. */
-	dec_rtc_base = (void *)KN01_RTC_BASE;
-	dec_kn_slot_size = KN01_SLOT_SIZE;
-
 	/* IRQ routing. */
 	memcpy(&dec_interrupt, &kn01_interrupt,
 		sizeof(kn01_interrupt));
@@ -233,7 +241,7 @@
 	[DEC_IRQ_HALT]		= DEC_CPU_IRQ_NR(KN230_CPU_INR_HALT),
 	[DEC_IRQ_ISDN]		= -1,
 	[DEC_IRQ_LANCE]		= DEC_CPU_IRQ_NR(KN230_CPU_INR_LANCE),
-	[DEC_IRQ_MEMORY]	= DEC_CPU_IRQ_NR(KN230_CPU_INR_MEMORY),
+	[DEC_IRQ_BUS]		= DEC_CPU_IRQ_NR(KN230_CPU_INR_BUS),
 	[DEC_IRQ_PSU]		= -1,
 	[DEC_IRQ_RTC]		= DEC_CPU_IRQ_NR(KN230_CPU_INR_RTC),
 	[DEC_IRQ_SCC0]		= -1,
@@ -256,10 +264,10 @@
 	[DEC_IRQ_SCC0A_RXDMA]	= -1,
 	[DEC_IRQ_SCC0A_TXERR]	= -1,
 	[DEC_IRQ_SCC0A_TXDMA]	= -1,
-	[DEC_IRQ_SCC0B_RXERR]	= -1,
-	[DEC_IRQ_SCC0B_RXDMA]	= -1,
-	[DEC_IRQ_SCC0B_TXERR]	= -1,
-	[DEC_IRQ_SCC0B_TXDMA]	= -1,
+	[DEC_IRQ_AB_RXERR]	= -1,
+	[DEC_IRQ_AB_RXDMA]	= -1,
+	[DEC_IRQ_AB_TXERR]	= -1,
+	[DEC_IRQ_AB_TXDMA]	= -1,
 	[DEC_IRQ_SCC1A_RXERR]	= -1,
 	[DEC_IRQ_SCC1A_RXDMA]	= -1,
 	[DEC_IRQ_SCC1A_TXERR]	= -1,
@@ -267,24 +275,20 @@
 };
 
 static int_ptr kn230_cpu_mask_nr_tbl[][2] __initdata = {
-	{ { i: DEC_CPU_IRQ_MASK(KN230_CPU_INR_MEMORY) },
-		{ i: DEC_CPU_IRQ_NR(KN230_CPU_INR_MEMORY) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN230_CPU_INR_RTC) },
-		{ i: DEC_CPU_IRQ_NR(KN230_CPU_INR_RTC) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN230_CPU_INR_DZ11) },
-		{ i: DEC_CPU_IRQ_NR(KN230_CPU_INR_DZ11) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN230_CPU_INR_SII) },
-		{ i: DEC_CPU_IRQ_NR(KN230_CPU_INR_SII) } },
-	{ { i: DEC_CPU_IRQ_ALL },
-		{ p: cpu_all_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN230_CPU_INR_BUS) },
+		{ .i = DEC_CPU_IRQ_NR(KN230_CPU_INR_BUS) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN230_CPU_INR_RTC) },
+		{ .i = DEC_CPU_IRQ_NR(KN230_CPU_INR_RTC) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN230_CPU_INR_DZ11) },
+		{ .i = DEC_CPU_IRQ_NR(KN230_CPU_INR_DZ11) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN230_CPU_INR_SII) },
+		{ .i = DEC_CPU_IRQ_NR(KN230_CPU_INR_SII) } },
+	{ { .i = DEC_CPU_IRQ_ALL },
+		{ .p = cpu_all_int } },
 };
 
 void __init dec_init_kn230(void)
 {
-	/* Setup some memory addresses. */
-	dec_rtc_base = (void *)KN01_RTC_BASE;
-	dec_kn_slot_size = KN01_SLOT_SIZE;
-
 	/* IRQ routing. */
 	memcpy(&dec_interrupt, &kn230_interrupt,
 		sizeof(kn230_interrupt));
@@ -312,7 +316,7 @@
 	[DEC_IRQ_HALT]		= -1,
 	[DEC_IRQ_ISDN]		= -1,
 	[DEC_IRQ_LANCE]		= KN02_IRQ_NR(KN02_CSR_INR_LANCE),
-	[DEC_IRQ_MEMORY]	= DEC_CPU_IRQ_NR(KN02_CPU_INR_MEMORY),
+	[DEC_IRQ_BUS]		= DEC_CPU_IRQ_NR(KN02_CPU_INR_BUS),
 	[DEC_IRQ_PSU]		= -1,
 	[DEC_IRQ_RTC]		= DEC_CPU_IRQ_NR(KN02_CPU_INR_RTC),
 	[DEC_IRQ_SCC0]		= -1,
@@ -335,10 +339,10 @@
 	[DEC_IRQ_SCC0A_RXDMA]	= -1,
 	[DEC_IRQ_SCC0A_TXERR]	= -1,
 	[DEC_IRQ_SCC0A_TXDMA]	= -1,
-	[DEC_IRQ_SCC0B_RXERR]	= -1,
-	[DEC_IRQ_SCC0B_RXDMA]	= -1,
-	[DEC_IRQ_SCC0B_TXERR]	= -1,
-	[DEC_IRQ_SCC0B_TXDMA]	= -1,
+	[DEC_IRQ_AB_RXERR]	= -1,
+	[DEC_IRQ_AB_RXDMA]	= -1,
+	[DEC_IRQ_AB_TXERR]	= -1,
+	[DEC_IRQ_AB_TXDMA]	= -1,
 	[DEC_IRQ_SCC1A_RXERR]	= -1,
 	[DEC_IRQ_SCC1A_RXDMA]	= -1,
 	[DEC_IRQ_SCC1A_TXERR]	= -1,
@@ -346,39 +350,35 @@
 };
 
 static int_ptr kn02_cpu_mask_nr_tbl[][2] __initdata = {
-	{ { i: DEC_CPU_IRQ_MASK(KN02_CPU_INR_MEMORY) },
-		{ i: DEC_CPU_IRQ_NR(KN02_CPU_INR_MEMORY) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02_CPU_INR_RTC) },
-		{ i: DEC_CPU_IRQ_NR(KN02_CPU_INR_RTC) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02_CPU_INR_CASCADE) },
-		{ p: kn02_io_int } },
-	{ { i: DEC_CPU_IRQ_ALL },
-		{ p: cpu_all_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02_CPU_INR_BUS) },
+		{ .i = DEC_CPU_IRQ_NR(KN02_CPU_INR_BUS) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02_CPU_INR_RTC) },
+		{ .i = DEC_CPU_IRQ_NR(KN02_CPU_INR_RTC) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02_CPU_INR_CASCADE) },
+		{ .p = kn02_io_int } },
+	{ { .i = DEC_CPU_IRQ_ALL },
+		{ .p = cpu_all_int } },
 };
 
 static int_ptr kn02_asic_mask_nr_tbl[][2] __initdata = {
-	{ { i: KN02_IRQ_MASK(KN02_CSR_INR_DZ11) },
-		{ i: KN02_IRQ_NR(KN02_CSR_INR_DZ11) } },
-	{ { i: KN02_IRQ_MASK(KN02_CSR_INR_ASC) },
-		{ i: KN02_IRQ_NR(KN02_CSR_INR_ASC) } },
-	{ { i: KN02_IRQ_MASK(KN02_CSR_INR_LANCE) },
-		{ i: KN02_IRQ_NR(KN02_CSR_INR_LANCE) } },
-	{ { i: KN02_IRQ_MASK(KN02_CSR_INR_TC2) },
-		{ i: KN02_IRQ_NR(KN02_CSR_INR_TC2) } },
-	{ { i: KN02_IRQ_MASK(KN02_CSR_INR_TC1) },
-		{ i: KN02_IRQ_NR(KN02_CSR_INR_TC1) } },
-	{ { i: KN02_IRQ_MASK(KN02_CSR_INR_TC0) },
-		{ i: KN02_IRQ_NR(KN02_CSR_INR_TC0) } },
-	{ { i: KN02_IRQ_ALL },
-		{ p: kn02_all_int } },
+	{ { .i = KN02_IRQ_MASK(KN02_CSR_INR_DZ11) },
+		{ .i = KN02_IRQ_NR(KN02_CSR_INR_DZ11) } },
+	{ { .i = KN02_IRQ_MASK(KN02_CSR_INR_ASC) },
+		{ .i = KN02_IRQ_NR(KN02_CSR_INR_ASC) } },
+	{ { .i = KN02_IRQ_MASK(KN02_CSR_INR_LANCE) },
+		{ .i = KN02_IRQ_NR(KN02_CSR_INR_LANCE) } },
+	{ { .i = KN02_IRQ_MASK(KN02_CSR_INR_TC2) },
+		{ .i = KN02_IRQ_NR(KN02_CSR_INR_TC2) } },
+	{ { .i = KN02_IRQ_MASK(KN02_CSR_INR_TC1) },
+		{ .i = KN02_IRQ_NR(KN02_CSR_INR_TC1) } },
+	{ { .i = KN02_IRQ_MASK(KN02_CSR_INR_TC0) },
+		{ .i = KN02_IRQ_NR(KN02_CSR_INR_TC0) } },
+	{ { .i = KN02_IRQ_ALL },
+		{ .p = kn02_all_int } },
 };
 
 void __init dec_init_kn02(void)
 {
-	/* Setup some memory addresses. */
-	dec_rtc_base = (void *)KN02_RTC_BASE;
-	dec_kn_slot_size = KN02_SLOT_SIZE;
-
 	/* IRQ routing. */
 	memcpy(&dec_interrupt, &kn02_interrupt,
 		sizeof(kn02_interrupt));
@@ -413,7 +413,7 @@
 	[DEC_IRQ_HALT]		= DEC_CPU_IRQ_NR(KN02BA_CPU_INR_HALT),
 	[DEC_IRQ_ISDN]		= -1,
 	[DEC_IRQ_LANCE]		= IO_IRQ_NR(KN02BA_IO_INR_LANCE),
-	[DEC_IRQ_MEMORY]	= IO_IRQ_NR(KN02BA_IO_INR_MEMORY),
+	[DEC_IRQ_BUS]		= IO_IRQ_NR(KN02BA_IO_INR_BUS),
 	[DEC_IRQ_PSU]		= IO_IRQ_NR(KN02BA_IO_INR_PSU),
 	[DEC_IRQ_RTC]		= IO_IRQ_NR(KN02BA_IO_INR_RTC),
 	[DEC_IRQ_SCC0]		= IO_IRQ_NR(KN02BA_IO_INR_SCC0),
@@ -436,10 +436,10 @@
 	[DEC_IRQ_SCC0A_RXDMA]	= IO_IRQ_NR(IO_INR_SCC0A_RXDMA),
 	[DEC_IRQ_SCC0A_TXERR]	= IO_IRQ_NR(IO_INR_SCC0A_TXERR),
 	[DEC_IRQ_SCC0A_TXDMA]	= IO_IRQ_NR(IO_INR_SCC0A_TXDMA),
-	[DEC_IRQ_SCC0B_RXERR]	= -1,
-	[DEC_IRQ_SCC0B_RXDMA]	= -1,
-	[DEC_IRQ_SCC0B_TXERR]	= -1,
-	[DEC_IRQ_SCC0B_TXDMA]	= -1,
+	[DEC_IRQ_AB_RXERR]	= -1,
+	[DEC_IRQ_AB_RXDMA]	= -1,
+	[DEC_IRQ_AB_TXERR]	= -1,
+	[DEC_IRQ_AB_TXDMA]	= -1,
 	[DEC_IRQ_SCC1A_RXERR]	= IO_IRQ_NR(IO_INR_SCC1A_RXERR),
 	[DEC_IRQ_SCC1A_RXDMA]	= IO_IRQ_NR(IO_INR_SCC1A_RXDMA),
 	[DEC_IRQ_SCC1A_TXERR]	= IO_IRQ_NR(IO_INR_SCC1A_TXERR),
@@ -447,44 +447,39 @@
 };
 
 static int_ptr kn02ba_cpu_mask_nr_tbl[][2] __initdata = {
-	{ { i: DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_CASCADE) },
-		{ p: kn02xa_io_int } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_TC2) },
-		{ i: DEC_CPU_IRQ_NR(KN02BA_CPU_INR_TC2) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_TC1) },
-		{ i: DEC_CPU_IRQ_NR(KN02BA_CPU_INR_TC1) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_TC0) },
-		{ i: DEC_CPU_IRQ_NR(KN02BA_CPU_INR_TC0) } },
-	{ { i: DEC_CPU_IRQ_ALL },
-		{ p: cpu_all_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_CASCADE) },
+		{ .p = kn02xa_io_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_TC2) },
+		{ .i = DEC_CPU_IRQ_NR(KN02BA_CPU_INR_TC2) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_TC1) },
+		{ .i = DEC_CPU_IRQ_NR(KN02BA_CPU_INR_TC1) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02BA_CPU_INR_TC0) },
+		{ .i = DEC_CPU_IRQ_NR(KN02BA_CPU_INR_TC0) } },
+	{ { .i = DEC_CPU_IRQ_ALL },
+		{ .p = cpu_all_int } },
 };
 
 static int_ptr kn02ba_asic_mask_nr_tbl[][2] __initdata = {
-	{ { i: IO_IRQ_MASK(KN02BA_IO_INR_MEMORY) },
-		{ i: IO_IRQ_NR(KN02BA_IO_INR_MEMORY) } },
-	{ { i: IO_IRQ_MASK(KN02BA_IO_INR_RTC) },
-		{ i: IO_IRQ_NR(KN02BA_IO_INR_RTC) } },
-	{ { i: IO_IRQ_DMA },
-		{ p: asic_dma_int } },
-	{ { i: IO_IRQ_MASK(KN02BA_IO_INR_SCC0) },
-		{ i: IO_IRQ_NR(KN02BA_IO_INR_SCC0) } },
-	{ { i: IO_IRQ_MASK(KN02BA_IO_INR_SCC1) },
-		{ i: IO_IRQ_NR(KN02BA_IO_INR_SCC1) } },
-	{ { i: IO_IRQ_MASK(KN02BA_IO_INR_ASC) },
-		{ i: IO_IRQ_NR(KN02BA_IO_INR_ASC) } },
-	{ { i: IO_IRQ_MASK(KN02BA_IO_INR_LANCE) },
-		{ i: IO_IRQ_NR(KN02BA_IO_INR_LANCE) } },
-	{ { i: IO_IRQ_ALL },
-		{ p: asic_all_int } },
+	{ { .i = IO_IRQ_MASK(KN02BA_IO_INR_BUS) },
+		{ .i = IO_IRQ_NR(KN02BA_IO_INR_BUS) } },
+	{ { .i = IO_IRQ_MASK(KN02BA_IO_INR_RTC) },
+		{ .i = IO_IRQ_NR(KN02BA_IO_INR_RTC) } },
+	{ { .i = IO_IRQ_DMA },
+		{ .p = asic_dma_int } },
+	{ { .i = IO_IRQ_MASK(KN02BA_IO_INR_SCC0) },
+		{ .i = IO_IRQ_NR(KN02BA_IO_INR_SCC0) } },
+	{ { .i = IO_IRQ_MASK(KN02BA_IO_INR_SCC1) },
+		{ .i = IO_IRQ_NR(KN02BA_IO_INR_SCC1) } },
+	{ { .i = IO_IRQ_MASK(KN02BA_IO_INR_ASC) },
+		{ .i = IO_IRQ_NR(KN02BA_IO_INR_ASC) } },
+	{ { .i = IO_IRQ_MASK(KN02BA_IO_INR_LANCE) },
+		{ .i = IO_IRQ_NR(KN02BA_IO_INR_LANCE) } },
+	{ { .i = IO_IRQ_ALL },
+		{ .p = asic_all_int } },
 };
 
 void __init dec_init_kn02ba(void)
 {
-	/* Setup some memory addresses. */
-	ioasic_base = (void *)KN02BA_IOASIC_BASE;
-	dec_rtc_base = (void *)KN02BA_RTC_BASE;
-	dec_kn_slot_size = IOASIC_SLOT_SIZE;
-
 	/* IRQ routing. */
 	memcpy(&dec_interrupt, &kn02ba_interrupt,
 		sizeof(kn02ba_interrupt));
@@ -519,7 +514,7 @@
 	[DEC_IRQ_HALT]		= DEC_CPU_IRQ_NR(KN02CA_CPU_INR_HALT),
 	[DEC_IRQ_ISDN]		= IO_IRQ_NR(KN02CA_IO_INR_ISDN),
 	[DEC_IRQ_LANCE]		= IO_IRQ_NR(KN02CA_IO_INR_LANCE),
-	[DEC_IRQ_MEMORY]	= DEC_CPU_IRQ_NR(KN02CA_CPU_INR_MEMORY),
+	[DEC_IRQ_BUS]		= DEC_CPU_IRQ_NR(KN02CA_CPU_INR_BUS),
 	[DEC_IRQ_PSU]		= -1,
 	[DEC_IRQ_RTC]		= DEC_CPU_IRQ_NR(KN02CA_CPU_INR_RTC),
 	[DEC_IRQ_SCC0]		= IO_IRQ_NR(KN02CA_IO_INR_SCC0),
@@ -542,10 +537,10 @@
 	[DEC_IRQ_SCC0A_RXDMA]	= IO_IRQ_NR(IO_INR_SCC0A_RXDMA),
 	[DEC_IRQ_SCC0A_TXERR]	= IO_IRQ_NR(IO_INR_SCC0A_TXERR),
 	[DEC_IRQ_SCC0A_TXDMA]	= IO_IRQ_NR(IO_INR_SCC0A_TXDMA),
-	[DEC_IRQ_SCC0B_RXERR]	= IO_IRQ_NR(IO_INR_SCC0B_RXERR),
-	[DEC_IRQ_SCC0B_RXDMA]	= IO_IRQ_NR(IO_INR_SCC0B_RXDMA),
-	[DEC_IRQ_SCC0B_TXERR]	= IO_IRQ_NR(IO_INR_SCC0B_TXERR),
-	[DEC_IRQ_SCC0B_TXDMA]	= IO_IRQ_NR(IO_INR_SCC0B_TXDMA),
+	[DEC_IRQ_AB_RXERR]	= IO_IRQ_NR(IO_INR_AB_RXERR),
+	[DEC_IRQ_AB_RXDMA]	= IO_IRQ_NR(IO_INR_AB_RXDMA),
+	[DEC_IRQ_AB_TXERR]	= IO_IRQ_NR(IO_INR_AB_TXERR),
+	[DEC_IRQ_AB_TXDMA]	= IO_IRQ_NR(IO_INR_AB_TXDMA),
 	[DEC_IRQ_SCC1A_RXERR]	= -1,
 	[DEC_IRQ_SCC1A_RXDMA]	= -1,
 	[DEC_IRQ_SCC1A_TXERR]	= -1,
@@ -553,40 +548,35 @@
 };
 
 static int_ptr kn02ca_cpu_mask_nr_tbl[][2] __initdata = {
-	{ { i: DEC_CPU_IRQ_MASK(KN02CA_CPU_INR_MEMORY) },
-		{ i: DEC_CPU_IRQ_NR(KN02CA_CPU_INR_MEMORY) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02CA_CPU_INR_RTC) },
-		{ i: DEC_CPU_IRQ_NR(KN02CA_CPU_INR_RTC) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN02CA_CPU_INR_CASCADE) },
-		{ p: kn02xa_io_int } },
-	{ { i: DEC_CPU_IRQ_ALL },
-		{ p: cpu_all_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02CA_CPU_INR_BUS) },
+		{ .i = DEC_CPU_IRQ_NR(KN02CA_CPU_INR_BUS) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02CA_CPU_INR_RTC) },
+		{ .i = DEC_CPU_IRQ_NR(KN02CA_CPU_INR_RTC) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN02CA_CPU_INR_CASCADE) },
+		{ .p = kn02xa_io_int } },
+	{ { .i = DEC_CPU_IRQ_ALL },
+		{ .p = cpu_all_int } },
 };
 
 static int_ptr kn02ca_asic_mask_nr_tbl[][2] __initdata = {
-	{ { i: IO_IRQ_DMA },
-		{ p: asic_dma_int } },
-	{ { i: IO_IRQ_MASK(KN02CA_IO_INR_SCC0) },
-		{ i: IO_IRQ_NR(KN02CA_IO_INR_SCC0) } },
-	{ { i: IO_IRQ_MASK(KN02CA_IO_INR_ASC) },
-		{ i: IO_IRQ_NR(KN02CA_IO_INR_ASC) } },
-	{ { i: IO_IRQ_MASK(KN02CA_IO_INR_LANCE) },
-		{ i: IO_IRQ_NR(KN02CA_IO_INR_LANCE) } },
-	{ { i: IO_IRQ_MASK(KN02CA_IO_INR_TC1) },
-		{ i: IO_IRQ_NR(KN02CA_IO_INR_TC1) } },
-	{ { i: IO_IRQ_MASK(KN02CA_IO_INR_TC0) },
-		{ i: IO_IRQ_NR(KN02CA_IO_INR_TC0) } },
-	{ { i: IO_IRQ_ALL },
-		{ p: asic_all_int } },
+	{ { .i = IO_IRQ_DMA },
+		{ .p = asic_dma_int } },
+	{ { .i = IO_IRQ_MASK(KN02CA_IO_INR_SCC0) },
+		{ .i = IO_IRQ_NR(KN02CA_IO_INR_SCC0) } },
+	{ { .i = IO_IRQ_MASK(KN02CA_IO_INR_ASC) },
+		{ .i = IO_IRQ_NR(KN02CA_IO_INR_ASC) } },
+	{ { .i = IO_IRQ_MASK(KN02CA_IO_INR_LANCE) },
+		{ .i = IO_IRQ_NR(KN02CA_IO_INR_LANCE) } },
+	{ { .i = IO_IRQ_MASK(KN02CA_IO_INR_TC1) },
+		{ .i = IO_IRQ_NR(KN02CA_IO_INR_TC1) } },
+	{ { .i = IO_IRQ_MASK(KN02CA_IO_INR_TC0) },
+		{ .i = IO_IRQ_NR(KN02CA_IO_INR_TC0) } },
+	{ { .i = IO_IRQ_ALL },
+		{ .p = asic_all_int } },
 };
 
 void __init dec_init_kn02ca(void)
 {
-	/* Setup some memory addresses. */
-	ioasic_base = (void *)KN02CA_IOASIC_BASE;
-	dec_rtc_base = (void *)KN02CA_RTC_BASE;
-	dec_kn_slot_size = IOASIC_SLOT_SIZE;
-
 	/* IRQ routing. */
 	memcpy(&dec_interrupt, &kn02ca_interrupt,
 		sizeof(kn02ca_interrupt));
@@ -608,7 +598,7 @@
 /*
  * Machine-specific initialisation for KN03, aka DS5000/240,
  * aka 3max+ and DS5900, aka BIGmax.  Also applies to KN05, aka
- * DS5000/260, aka 4max+ and DS5900-260.
+ * DS5000/260, aka 4max+ and DS5900/260.
  */
 static int kn03_interrupt[DEC_NR_INTS] __initdata = {
 	[DEC_IRQ_CASCADE]	= DEC_CPU_IRQ_NR(KN03_CPU_INR_CASCADE),
@@ -621,7 +611,7 @@
 	[DEC_IRQ_HALT]		= DEC_CPU_IRQ_NR(KN03_CPU_INR_HALT),
 	[DEC_IRQ_ISDN]		= -1,
 	[DEC_IRQ_LANCE]		= IO_IRQ_NR(KN03_IO_INR_LANCE),
-	[DEC_IRQ_MEMORY]	= DEC_CPU_IRQ_NR(KN03_CPU_INR_MEMORY),
+	[DEC_IRQ_BUS]		= DEC_CPU_IRQ_NR(KN03_CPU_INR_BUS),
 	[DEC_IRQ_PSU]		= IO_IRQ_NR(KN03_IO_INR_PSU),
 	[DEC_IRQ_RTC]		= DEC_CPU_IRQ_NR(KN03_CPU_INR_RTC),
 	[DEC_IRQ_SCC0]		= IO_IRQ_NR(KN03_IO_INR_SCC0),
@@ -644,10 +634,10 @@
 	[DEC_IRQ_SCC0A_RXDMA]	= IO_IRQ_NR(IO_INR_SCC0A_RXDMA),
 	[DEC_IRQ_SCC0A_TXERR]	= IO_IRQ_NR(IO_INR_SCC0A_TXERR),
 	[DEC_IRQ_SCC0A_TXDMA]	= IO_IRQ_NR(IO_INR_SCC0A_TXDMA),
-	[DEC_IRQ_SCC0B_RXERR]	= -1,
-	[DEC_IRQ_SCC0B_RXDMA]	= -1,
-	[DEC_IRQ_SCC0B_TXERR]	= -1,
-	[DEC_IRQ_SCC0B_TXDMA]	= -1,
+	[DEC_IRQ_AB_RXERR]	= -1,
+	[DEC_IRQ_AB_RXDMA]	= -1,
+	[DEC_IRQ_AB_TXERR]	= -1,
+	[DEC_IRQ_AB_TXDMA]	= -1,
 	[DEC_IRQ_SCC1A_RXERR]	= IO_IRQ_NR(IO_INR_SCC1A_RXERR),
 	[DEC_IRQ_SCC1A_RXDMA]	= IO_IRQ_NR(IO_INR_SCC1A_RXDMA),
 	[DEC_IRQ_SCC1A_TXERR]	= IO_IRQ_NR(IO_INR_SCC1A_TXERR),
@@ -655,44 +645,39 @@
 };
 
 static int_ptr kn03_cpu_mask_nr_tbl[][2] __initdata = {
-	{ { i: DEC_CPU_IRQ_MASK(KN03_CPU_INR_MEMORY) },
-		{ i: DEC_CPU_IRQ_NR(KN03_CPU_INR_MEMORY) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN03_CPU_INR_RTC) },
-		{ i: DEC_CPU_IRQ_NR(KN03_CPU_INR_RTC) } },
-	{ { i: DEC_CPU_IRQ_MASK(KN03_CPU_INR_CASCADE) },
-		{ p: kn03_io_int } },
-	{ { i: DEC_CPU_IRQ_ALL },
-		{ p: cpu_all_int } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN03_CPU_INR_BUS) },
+		{ .i = DEC_CPU_IRQ_NR(KN03_CPU_INR_BUS) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN03_CPU_INR_RTC) },
+		{ .i = DEC_CPU_IRQ_NR(KN03_CPU_INR_RTC) } },
+	{ { .i = DEC_CPU_IRQ_MASK(KN03_CPU_INR_CASCADE) },
+		{ .p = kn03_io_int } },
+	{ { .i = DEC_CPU_IRQ_ALL },
+		{ .p = cpu_all_int } },
 };
 
 static int_ptr kn03_asic_mask_nr_tbl[][2] __initdata = {
-	{ { i: IO_IRQ_DMA },
-		{ p: asic_dma_int } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_SCC0) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_SCC0) } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_SCC1) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_SCC1) } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_ASC) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_ASC) } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_LANCE) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_LANCE) } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_TC2) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_TC2) } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_TC1) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_TC1) } },
-	{ { i: IO_IRQ_MASK(KN03_IO_INR_TC0) },
-		{ i: IO_IRQ_NR(KN03_IO_INR_TC0) } },
-	{ { i: IO_IRQ_ALL },
-		{ p: asic_all_int } },
+	{ { .i = IO_IRQ_DMA },
+		{ .p = asic_dma_int } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_SCC0) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_SCC0) } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_SCC1) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_SCC1) } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_ASC) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_ASC) } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_LANCE) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_LANCE) } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_TC2) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_TC2) } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_TC1) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_TC1) } },
+	{ { .i = IO_IRQ_MASK(KN03_IO_INR_TC0) },
+		{ .i = IO_IRQ_NR(KN03_IO_INR_TC0) } },
+	{ { .i = IO_IRQ_ALL },
+		{ .p = asic_all_int } },
 };
 
 void __init dec_init_kn03(void)
 {
-	/* Setup some memory addresses.  */
-	ioasic_base = (void *)KN03_IOASIC_BASE;
-	dec_rtc_base = (void *)KN03_RTC_BASE;
-	dec_kn_slot_size = IOASIC_SLOT_SIZE;
-
 	/* IRQ routing. */
 	memcpy(&dec_interrupt, &kn03_interrupt,
 		sizeof(kn03_interrupt));
@@ -727,6 +712,7 @@
 		dec_init_kn02ba();
 		break;
 	case MACH_DS5000_2X0:	/* DS5000/240 3max+ */
+	case MACH_DS5900:	/* DS5900 bigmax */
 		dec_init_kn03();
 		break;
 	case MACH_DS5000_XX:	/* Personal DS5000/xx */
@@ -745,7 +731,7 @@
 	set_except_vector(0, decstation_handle_int);
 
 	/* Free the FPU interrupt if the exception is present. */
-	if (!(mips_cpu.options & MIPS_CPU_NOFPUEX)) {
+	if (!cpu_has_nofpuex) {
 		cpu_fpu_mask = 0;
 		dec_interrupt[DEC_IRQ_FPU] = -1;
 	}
@@ -756,12 +742,15 @@
 	if (dec_interrupt[DEC_IRQ_CASCADE] >= 0)
 		setup_irq(dec_interrupt[DEC_IRQ_CASCADE], &ioirq);
 
+	/* Register the bus error interrupt. */
+	if (dec_interrupt[DEC_IRQ_BUS] >= 0 && busirq.handler)
+		setup_irq(dec_interrupt[DEC_IRQ_BUS], &busirq);
+
 	/* Register the HALT interrupt. */
 	if (dec_interrupt[DEC_IRQ_HALT] >= 0)
 		setup_irq(dec_interrupt[DEC_IRQ_HALT], &haltirq);
 }
 
 EXPORT_SYMBOL(ioasic_base);
-EXPORT_SYMBOL(dec_rtc_base);
 EXPORT_SYMBOL(dec_kn_slot_size);
 EXPORT_SYMBOL(dec_interrupt);
diff -urN linux-2.4.21-bk33/arch/mips/dec/time.c linux-2.4.21-bk34/arch/mips/dec/time.c
--- linux-2.4.21-bk33/arch/mips/dec/time.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/time.c	2003-08-15 02:54:46.000000000 -0700
@@ -2,278 +2,103 @@
  *  linux/arch/mips/dec/time.c
  *
  *  Copyright (C) 1991, 1992, 1995  Linus Torvalds
- *  Copyright (C) 2000  Maciej W. Rozycki
+ *  Copyright (C) 2000, 2003  Maciej W. Rozycki
  *
  * This file contains the time handling details for PC-style clocks as
  * found in some MIPS systems.
  *
  */
-#include <linux/types.h>
 #include <linux/errno.h>
 #include <linux/init.h>
-#include <linux/sched.h>
+#include <linux/interrupt.h>
 #include <linux/kernel.h>
+#include <linux/mm.h>
 #include <linux/param.h>
+#include <linux/sched.h>
 #include <linux/string.h>
-#include <linux/mm.h>
-#include <linux/interrupt.h>
+#include <linux/types.h>
 
-#include <asm/cpu.h>
 #include <asm/bootinfo.h>
-#include <asm/mipsregs.h>
+#include <asm/cpu.h>
+#include <asm/div64.h>
 #include <asm/io.h>
 #include <asm/irq.h>
-#include <asm/dec/machtype.h>
+#include <asm/mipsregs.h>
+#include <asm/time.h>
+
+#include <asm/dec/interrupts.h>
 #include <asm/dec/ioasic.h>
 #include <asm/dec/ioasic_addrs.h>
+#include <asm/dec/machtype.h>
 
 #include <linux/mc146818rtc.h>
 #include <linux/timex.h>
 
-#include <asm/div64.h>
-
-extern void (*board_time_init)(struct irqaction *irq);
-
-extern volatile unsigned long wall_jiffies;
-extern rwlock_t xtime_lock;
 
-/*
- * Change this if you have some constant time drift
- */
-/* This is the value for the PC-style PICs. */
-/* #define USECS_PER_JIFFY (1000020/HZ) */
-
-/* This is for machines which generate the exact clock. */
-#define USECS_PER_JIFFY (1000000/HZ)
-#define USECS_PER_JIFFY_FRAC ((u32)((1000000ULL << 32) / HZ))
-
-/* Cycle counter value at the previous timer interrupt.. */
-
-static unsigned int timerhi, timerlo;
-
-/*
- * Cached "1/(clocks per usec)*2^32" value.
- * It has to be recalculated once each jiffy.
- */
-static unsigned long cached_quotient = 0;
-
-/* Last jiffy when do_fast_gettimeoffset() was called. */
-static unsigned long last_jiffies = 0;
-
-/*
- * On MIPS only R4000 and better have a cycle counter.
- *
- * FIXME: Does playing with the RP bit in c0_status interfere with this code?
- */
-static unsigned long do_fast_gettimeoffset(void)
+static unsigned long dec_rtc_get_time(void)
 {
-	u32 count;
-	unsigned long res, tmp;
-	unsigned long quotient;
-
-	tmp = jiffies;
-
-	quotient = cached_quotient;
-
-	if (last_jiffies != tmp) {
-	    last_jiffies = tmp;
-	    if (last_jiffies != 0) {
-		unsigned long r0;
-		__asm__(".set	push\n\t"
-			".set	mips3\n\t"
-			"lwu	%0,%3\n\t"
-			"dsll32	%1,%2,0\n\t"
-			"or	%1,%1,%0\n\t"
-			"ddivu	$0,%1,%4\n\t"
-			"mflo	%1\n\t"
-			"dsll32	%0,%5,0\n\t"
-			"or	%0,%0,%6\n\t"
-			"ddivu	$0,%0,%1\n\t"
-			"mflo	%0\n\t"
-			".set	pop"
-			: "=&r" (quotient), "=&r" (r0)
-			: "r" (timerhi), "m" (timerlo),
-			  "r" (tmp), "r" (USECS_PER_JIFFY),
-			  "r" (USECS_PER_JIFFY_FRAC));
-		cached_quotient = quotient;
-	    }
-	}
-	/* Get last timer tick in absolute kernel time */
-	count = read_32bit_cp0_register(CP0_COUNT);
-
-	/* .. relative to previous jiffy (32 bits is enough) */
-	count -= timerlo;
-//printk("count: %08lx, %08lx:%08lx\n", count, timerhi, timerlo);
-
-	__asm__("multu	%2,%3"
-		: "=l" (tmp), "=h" (res)
-		: "r" (count), "r" (quotient));
+	unsigned int year, mon, day, hour, min, sec, real_year;
+	int i;
 
-	/*
-	 * Due to possible jiffies inconsistencies, we need to check
-	 * the result so that we'll get a timer that is monotonic.
+	/* The Linux interpretation of the DS1287 clock register contents:
+	 * When the Update-In-Progress (UIP) flag goes from 1 to 0, the
+	 * RTC registers show the second which has precisely just started.
+	 * Let's hope other operating systems interpret the RTC the same way.
 	 */
-	if (res >= USECS_PER_JIFFY)
-		res = USECS_PER_JIFFY - 1;
-
-	return res;
-}
-
-static unsigned long do_ioasic_gettimeoffset(void)
-{
-	u32 count;
-	unsigned long res, tmp;
-	unsigned long quotient;
-
-	tmp = jiffies;
-
-	quotient = cached_quotient;
-
-	if (last_jiffies != tmp) {
-		last_jiffies = tmp;
-		if (last_jiffies != 0) {
-			unsigned long r0;
-			do_div64_32(r0, timerhi, timerlo, tmp);
-			do_div64_32(quotient, USECS_PER_JIFFY,
-				    USECS_PER_JIFFY_FRAC, r0);
-			cached_quotient = quotient;
-		}
+	/* read RTC exactly on falling edge of update flag */
+	for (i = 0; i < 1000000; i++)	/* may take up to 1 second... */
+		if (CMOS_READ(RTC_FREQ_SELECT) & RTC_UIP)
+			break;
+	for (i = 0; i < 1000000; i++)	/* must try at least 2.228 ms */
+		if (!(CMOS_READ(RTC_FREQ_SELECT) & RTC_UIP))
+			break;
+	/* Isn't this overkill?  UIP above should guarantee consistency */
+	do {
+		sec = CMOS_READ(RTC_SECONDS);
+		min = CMOS_READ(RTC_MINUTES);
+		hour = CMOS_READ(RTC_HOURS);
+		day = CMOS_READ(RTC_DAY_OF_MONTH);
+		mon = CMOS_READ(RTC_MONTH);
+		year = CMOS_READ(RTC_YEAR);
+	} while (sec != CMOS_READ(RTC_SECONDS));
+	if (!(CMOS_READ(RTC_CONTROL) & RTC_DM_BINARY) || RTC_ALWAYS_BCD) {
+		BCD_TO_BIN(sec);
+		BCD_TO_BIN(min);
+		BCD_TO_BIN(hour);
+		BCD_TO_BIN(day);
+		BCD_TO_BIN(mon);
+		BCD_TO_BIN(year);
 	}
-	/* Get last timer tick in absolute kernel time */
-	count = ioasic_read(FCTR);
-
-	/* .. relative to previous jiffy (32 bits is enough) */
-	count -= timerlo;
-//printk("count: %08x, %08x:%08x\n", count, timerhi, timerlo);
-
-	__asm__("multu	%2,%3"
-		: "=l" (tmp), "=h" (res)
-		: "r" (count), "r" (quotient));
-
-	/*
-	 * Due to possible jiffies inconsistencies, we need to check
-	 * the result so that we'll get a timer that is monotonic.
-	 */
-	if (res >= USECS_PER_JIFFY)
-        	res = USECS_PER_JIFFY - 1;
-
-	return res;
-}
-
-/* This function must be called with interrupts disabled
- * It was inspired by Steve McCanne's microtime-i386 for BSD.  -- jrs
- *
- * However, the pc-audio speaker driver changes the divisor so that
- * it gets interrupted rather more often - it loads 64 into the
- * counter rather than 11932! This has an adverse impact on
- * do_gettimeoffset() -- it stops working! What is also not
- * good is that the interval that our timer function gets called
- * is no longer 10.0002 ms, but 9.9767 ms. To get around this
- * would require using a different timing source. Maybe someone
- * could use the RTC - I know that this can interrupt at frequencies
- * ranging from 8192Hz to 2Hz. If I had the energy, I'd somehow fix
- * it so that at startup, the timer code in sched.c would select
- * using either the RTC or the 8253 timer. The decision would be
- * based on whether there was any other device around that needed
- * to trample on the 8253. I'd set up the RTC to interrupt at 1024 Hz,
- * and then do some jiggery to have a version of do_timer that
- * advanced the clock by 1/1024 s. Every time that reached over 1/100
- * of a second, then do all the old code. If the time was kept correct
- * then do_gettimeoffset could just return 0 - there is no low order
- * divider that can be accessed.
- *
- * Ideally, you would be able to use the RTC for the speaker driver,
- * but it appears that the speaker driver really needs interrupt more
- * often than every 120 us or so.
- *
- * Anyway, this needs more thought....          pjsg (1993-08-28)
- *
- * If you are really that interested, you should be reading
- * comp.protocols.time.ntp!
- */
-
-#define TICK_SIZE tick
-
-static unsigned long do_slow_gettimeoffset(void)
-{
 	/*
-	 * This is a kludge until I find a way for the
-	 * DECstations without bus cycle counter. HK
-	 */
-	return 0;
-}
-
-static unsigned long (*do_gettimeoffset) (void) = do_slow_gettimeoffset;
-
-/*
- * This version of gettimeofday has near microsecond resolution.
- */
-void do_gettimeofday(struct timeval *tv)
-{
-	unsigned long flags;
-
-	read_lock_irqsave(&xtime_lock, flags);
-	*tv = xtime;
-	tv->tv_usec += do_gettimeoffset();
-
-	/*
-	 * xtime is atomically updated in timer_bh. jiffies - wall_jiffies
-	 * is nonzero if the timer bottom half hasnt executed yet.
-	 */
-	if (jiffies - wall_jiffies)
-		tv->tv_usec += USECS_PER_JIFFY;
-
-	read_unlock_irqrestore(&xtime_lock, flags);
-
-	if (tv->tv_usec >= 1000000) {
-		tv->tv_usec -= 1000000;
-		tv->tv_sec++;
-	}
-}
-
-void do_settimeofday(struct timeval *tv)
-{
-	write_lock_irq(&xtime_lock);
-
-	/* This is revolting. We need to set the xtime.tv_usec
-	 * correctly. However, the value in this location is
-	 * is value at the last tick.
-	 * Discover what correction gettimeofday
-	 * would have done, and then undo it!
+	 * The PROM will reset the year to either '72 or '73.
+	 * Therefore we store the real year separately, in one
+	 * of unused BBU RAM locations.
 	 */
-	tv->tv_usec -= do_gettimeoffset();
-
-	if (tv->tv_usec < 0) {
-		tv->tv_usec += 1000000;
-		tv->tv_sec--;
-	}
-
-	xtime = *tv;
-	time_adjust = 0;		/* stop active adjtime() */
-	time_status |= STA_UNSYNC;
-	time_maxerror = NTP_PHASE_LIMIT;
-	time_esterror = NTP_PHASE_LIMIT;
+	real_year = CMOS_READ(RTC_DEC_YEAR);
+	year += real_year - 72 + 2000;
 
-	write_unlock_irq(&xtime_lock);
+	return mktime(year, mon, day, hour, min, sec);
 }
 
 /*
- * In order to set the CMOS clock precisely, set_rtc_mmss has to be
- * called 500 ms after the second nowtime has started, because when
+ * In order to set the CMOS clock precisely, dec_rtc_set_mmss has to
+ * be called 500 ms after the second nowtime has started, because when
  * nowtime is written into the registers of the CMOS clock, it will
- * jump to the next second precisely 500 ms later. Check the Motorola
- * MC146818A or Dallas DS12887 data sheet for details.
+ * jump to the next second precisely 500 ms later.  Check the Dallas
+ * DS1287 data sheet for details.
  */
-static int set_rtc_mmss(unsigned long nowtime)
+static int dec_rtc_set_mmss(unsigned long nowtime)
 {
 	int retval = 0;
 	int real_seconds, real_minutes, cmos_minutes;
 	unsigned char save_control, save_freq_select;
 
-	save_control = CMOS_READ(RTC_CONTROL);	/* tell the clock it's being set */
+	/* tell the clock it's being set */
+	save_control = CMOS_READ(RTC_CONTROL);
 	CMOS_WRITE((save_control | RTC_SET), RTC_CONTROL);
 
-	save_freq_select = CMOS_READ(RTC_FREQ_SELECT);	/* stop and reset prescaler */
+	/* stop and reset prescaler */
+	save_freq_select = CMOS_READ(RTC_FREQ_SELECT);
 	CMOS_WRITE((save_freq_select | RTC_DIV_RESET2), RTC_FREQ_SELECT);
 
 	cmos_minutes = CMOS_READ(RTC_MINUTES);
@@ -307,10 +132,9 @@
 	}
 
 	/* The following flags have to be released exactly in this order,
-	 * otherwise the DS12887 (popular MC146818A clone with integrated
-	 * battery and quartz) will not reset the oscillator and will not
-	 * update precisely 500 ms later. You won't find this mentioned in
-	 * the Dallas Semiconductor data sheets, but who believes data
+	 * otherwise the DS1287 will not reset the oscillator and will not
+	 * update precisely 500 ms later.  You won't find this mentioned
+	 * in the Dallas Semiconductor data sheets, but who believes data
 	 * sheets anyway ...                           -- Markus Kuhn
 	 */
 	CMOS_WRITE(save_control, RTC_CONTROL);
@@ -319,170 +143,45 @@
 	return retval;
 }
 
-/* last time the cmos clock got updated */
-static long last_rtc_update;
 
-/*
- * timer_interrupt() needs to keep up the real-time clock,
- * as well as call the "do_timer()" routine every clocktick
- */
-static void inline
-timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+static void dec_timer_ack(void)
 {
-	volatile unsigned char dummy;
-
-	dummy = CMOS_READ(RTC_REG_C);	/* ACK RTC Interrupt */
-
-	if (!user_mode(regs)) {
-		if (prof_buffer && current->pid) {
-			extern int _stext;
-			unsigned long pc = regs->cp0_epc;
-
-			pc -= (unsigned long) &_stext;
-			pc >>= prof_shift;
-			/*
-			 * Dont ignore out-of-bounds pc values silently,
-			 * put them into the last histogram slot, so if
-			 * present, they will show up as a sharp peak.
-			 */
-			if (pc > prof_len - 1)
-				pc = prof_len - 1;
-			atomic_inc((atomic_t *) & prof_buffer[pc]);
-		}
-	}
-	do_timer(regs);
-
-	/*
-	 * If we have an externally synchronized Linux clock, then update
-	 * CMOS clock accordingly every ~11 minutes. Set_rtc_mmss() has to be
-	 * called as close as possible to 500 ms before the new second starts.
-	 */
-	read_lock(&xtime_lock);
-	if ((time_status & STA_UNSYNC) == 0
-	    && xtime.tv_sec > last_rtc_update + 660
-	    && xtime.tv_usec >= 500000 - tick / 2
-	    && xtime.tv_usec <= 500000 + tick / 2) {
-		if (set_rtc_mmss(xtime.tv_sec) == 0)
-			last_rtc_update = xtime.tv_sec;
-		else
-			/* do it again in 60 s */
-			last_rtc_update = xtime.tv_sec - 600;
-	}
-	/* As we return to user mode fire off the other CPU schedulers.. this is
-	   basically because we don't yet share IRQ's around. This message is
-	   rigged to be safe on the 386 - basically it's a hack, so don't look
-	   closely for now.. */
-	/*smp_message_pass(MSG_ALL_BUT_SELF, MSG_RESCHEDULE, 0L, 0); */
-	read_unlock(&xtime_lock);
+	CMOS_READ(RTC_REG_C);			/* Ack the RTC interrupt.  */
 }
 
-static void r4k_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+static unsigned int dec_ioasic_hpt_read(void)
 {
-	unsigned int count;
-
 	/*
-	 * The cycle counter is only 32 bit which is good for about
-	 * a minute at current count rates of upto 150MHz or so.
+	 * The free-running counter is 32-bit which is good for about
+	 * 2 minutes, 50 seconds at possible count rates of up to 25MHz.
 	 */
-	count = read_32bit_cp0_register(CP0_COUNT);
-	timerhi += (count < timerlo);	/* Wrap around */
-	timerlo = count;
-
-	if (jiffies == ~0) {
-		/*
-		 * If jiffies is to overflow in this timer_interrupt we must
-		 * update the timer[hi]/[lo] to make do_fast_gettimeoffset()
-		 * quotient calc still valid. -arca
-		 */
-		write_32bit_cp0_register(CP0_COUNT, 0);
-		timerhi = timerlo = 0;
-	}
-
-	timer_interrupt(irq, dev_id, regs);
+	return ioasic_read(IO_REG_FCTR);
 }
 
-static void ioasic_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+static void dec_ioasic_hpt_init(unsigned int count)
 {
-	unsigned int count;
-
-	/*
-	 * The free-running counter is 32 bit which is good for about
-	 * 2 minutes, 50 seconds at possible count rates of upto 25MHz.
-	 */
-	count = ioasic_read(FCTR);
-	timerhi += (count < timerlo);	/* Wrap around */
-	timerlo = count;
-
-	if (jiffies == ~0) {
-		/*
-		 * If jiffies is to overflow in this timer_interrupt we must
-		 * update the timer[hi]/[lo] to make do_fast_gettimeoffset()
-		 * quotient calc still valid. -arca
-		 */
-		ioasic_write(FCTR, 0);
-		timerhi = timerlo = 0;
-	}
-
-	timer_interrupt(irq, dev_id, regs);
+	ioasic_write(IO_REG_FCTR, ioasic_read(IO_REG_FCTR) - count);
 }
 
-struct irqaction irq0 = {timer_interrupt, SA_INTERRUPT, 0,
-			 "timer", NULL, NULL};
 
-void __init time_init(void)
+void __init dec_time_init(void)
 {
-	unsigned int year, mon, day, hour, min, sec, real_year;
-	int i;
+	rtc_get_time = dec_rtc_get_time;
+	rtc_set_mmss = dec_rtc_set_mmss;
 
-	/* The Linux interpretation of the CMOS clock register contents:
-	 * When the Update-In-Progress (UIP) flag goes from 1 to 0, the
-	 * RTC registers show the second which has precisely just started.
-	 * Let's hope other operating systems interpret the RTC the same way.
-	 */
-	/* read RTC exactly on falling edge of update flag */
-	for (i = 0; i < 1000000; i++)	/* may take up to 1 second... */
-		if (CMOS_READ(RTC_FREQ_SELECT) & RTC_UIP)
-			break;
-	for (i = 0; i < 1000000; i++)	/* must try at least 2.228 ms */
-		if (!(CMOS_READ(RTC_FREQ_SELECT) & RTC_UIP))
-			break;
-	do {			/* Isn't this overkill ? UIP above should guarantee consistency */
-		sec = CMOS_READ(RTC_SECONDS);
-		min = CMOS_READ(RTC_MINUTES);
-		hour = CMOS_READ(RTC_HOURS);
-		day = CMOS_READ(RTC_DAY_OF_MONTH);
-		mon = CMOS_READ(RTC_MONTH);
-		year = CMOS_READ(RTC_YEAR);
-	} while (sec != CMOS_READ(RTC_SECONDS));
-	if (!(CMOS_READ(RTC_CONTROL) & RTC_DM_BINARY) || RTC_ALWAYS_BCD) {
-		BCD_TO_BIN(sec);
-		BCD_TO_BIN(min);
-		BCD_TO_BIN(hour);
-		BCD_TO_BIN(day);
-		BCD_TO_BIN(mon);
-		BCD_TO_BIN(year);
+	mips_timer_ack = dec_timer_ack;
+	if (!cpu_has_counter && IOASIC) {
+		/* For pre-R4k systems we use the I/O ASIC's counter.  */
+		mips_hpt_read = dec_ioasic_hpt_read;
+		mips_hpt_init = dec_ioasic_hpt_init;
 	}
-	/*
-	 * The PROM will reset the year to either '72 or '73.
-	 * Therefore we store the real year separately, in one
-	 * of unused BBU RAM locations.
-	 */
-	real_year = CMOS_READ(RTC_DEC_YEAR);
-	year += real_year - 72 + 2000;
+}
+
+void __init dec_timer_setup(struct irqaction *irq)
+{
+	/* Enable periodic DS1287 interrupts.  */
+	CMOS_WRITE(RTC_REF_CLCK_32KHZ | (16 - LOG_2_HZ), RTC_REG_A);
+	CMOS_WRITE(CMOS_READ(RTC_REG_B) | RTC_PIE, RTC_REG_B);
 
-	write_lock_irq(&xtime_lock);
-	xtime.tv_sec = mktime(year, mon, day, hour, min, sec);
-	xtime.tv_usec = 0;
-	write_unlock_irq(&xtime_lock);
-
-	if (mips_cpu.options & MIPS_CPU_COUNTER) {
-		write_32bit_cp0_register(CP0_COUNT, 0);
-		do_gettimeoffset = do_fast_gettimeoffset;
-		irq0.handler = r4k_timer_interrupt;
-	} else if (IOASIC) {
-		ioasic_write(FCTR, 0);
-		do_gettimeoffset = do_ioasic_gettimeoffset;
-		irq0.handler = ioasic_timer_interrupt;
-        }
-	board_time_init(&irq0);
+	setup_irq(dec_interrupt[DEC_IRQ_RTC], irq);
 }
diff -urN linux-2.4.21-bk33/arch/mips/dec/wbflush.c linux-2.4.21-bk34/arch/mips/dec/wbflush.c
--- linux-2.4.21-bk33/arch/mips/dec/wbflush.c	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/dec/wbflush.c	2003-08-15 02:54:46.000000000 -0700
@@ -39,6 +39,7 @@
 	case MACH_DS5000_1XX:	/* DS5000/100 3min */
 	case MACH_DS5000_XX:	/* Personal DS5000/2x */
 	case MACH_DS5000_2X0:	/* DS5000/240 3max+ */
+	case MACH_DS5900:	/* DS5900 bigmax */
 	default:
 		__wbflush = wbflush_mips;
 		break;
diff -urN linux-2.4.21-bk33/arch/mips/defconfig-decstation linux-2.4.21-bk34/arch/mips/defconfig-decstation
--- linux-2.4.21-bk33/arch/mips/defconfig-decstation	2002-11-28 15:53:10.000000000 -0800
+++ linux-2.4.21-bk34/arch/mips/defconfig-decstation	2003-08-15 02:54:46.000000000 -0700
@@ -21,17 +21,26 @@
 # Machine selection
 #
 # CONFIG_ACER_PICA_61 is not set
+# CONFIG_MIPS_BOSPORUS is not set
+# CONFIG_MIPS_MIRAGE is not set
+# CONFIG_MIPS_DB1000 is not set
+# CONFIG_MIPS_DB1100 is not set
+# CONFIG_MIPS_DB1500 is not set
 # CONFIG_MIPS_PB1000 is not set
 # CONFIG_MIPS_PB1100 is not set
 # CONFIG_MIPS_PB1500 is not set
-# CONFIG_ALGOR_P4032 is not set
+# CONFIG_MIPS_XXS1500 is not set
+# CONFIG_MIPS_MTX1 is not set
 # CONFIG_BAGET_MIPS is not set
+# CONFIG_CASIO_E55 is not set
 # CONFIG_MIPS_COBALT is not set
 CONFIG_DECSTATION=y
 # CONFIG_MIPS_EV64120 is not set
 # CONFIG_MIPS_EV96100 is not set
 # CONFIG_MIPS_IVR is not set
 # CONFIG_HP_LASERJET is not set
+# CONFIG_IBM_WORKPAD is not set
+# CONFIG_LASAT is not set
 # CONFIG_MIPS_ITE8172 is not set
 # CONFIG_MIPS_ATLAS is not set
 # CONFIG_MIPS_MAGNUM_4000 is not set
@@ -39,6 +48,7 @@
 # CONFIG_MIPS_SEAD is not set
 # CONFIG_MOMENCO_OCELOT is not set
 # CONFIG_MOMENCO_OCELOT_G is not set
+# CONFIG_MOMENCO_OCELOT_C is not set
 # CONFIG_DDB5074 is not set
 # CONFIG_DDB5476 is not set
 # CONFIG_DDB5477 is not set
@@ -48,16 +58,21 @@
 # CONFIG_NINO is not set
 # CONFIG_SGI_IP22 is not set
 # CONFIG_SGI_IP27 is not set
-# CONFIG_SGI_IP32 is not set
 # CONFIG_SIBYTE_SB1xxx_SOC is not set
 # CONFIG_SNI_RM200_PCI is not set
+# CONFIG_TANBAC_TB0226 is not set
+# CONFIG_TANBAC_TB0229 is not set
 # CONFIG_TOSHIBA_JMR3927 is not set
+# CONFIG_TOSHIBA_RBTX4927 is not set
+# CONFIG_VICTOR_MPC30X is not set
 # CONFIG_ZAO_CAPCELLA is not set
 # CONFIG_HIGHMEM is not set
 CONFIG_RWSEM_GENERIC_SPINLOCK=y
 # CONFIG_RWSEM_XCHGADD_ALGORITHM is not set
+CONFIG_BOOT_ELF32=y
 CONFIG_IRQ_CPU=y
-CONFIG_NEW_IRQ=y
+CONFIG_L1_CACHE_SHIFT=4
+CONFIG_NEW_TIME_C=y
 CONFIG_NONCOHERENT_IO=y
 # CONFIG_MIPS_AU1000 is not set
 
@@ -108,9 +123,10 @@
 # CONFIG_BINFMT_AOUT is not set
 CONFIG_BINFMT_ELF=y
 # CONFIG_MIPS32_COMPAT is not set
+# CONFIG_MIPS32_O32 is not set
+# CONFIG_MIPS32_N32 is not set
 # CONFIG_BINFMT_ELF32 is not set
 # CONFIG_BINFMT_MISC is not set
-# CONFIG_PM is not set
 
 #
 # Memory Technology Devices (MTD)
@@ -263,6 +279,7 @@
 # CONFIG_SCSI_AHA1740 is not set
 # CONFIG_SCSI_AACRAID is not set
 # CONFIG_SCSI_AIC7XXX is not set
+# CONFIG_SCSI_AIC79XX is not set
 # CONFIG_SCSI_AIC7XXX_OLD is not set
 # CONFIG_SCSI_DPT_I2O is not set
 # CONFIG_SCSI_ADVANSYS is not set
@@ -291,6 +308,7 @@
 # CONFIG_SCSI_SYM53C416 is not set
 # CONFIG_SCSI_T128 is not set
 # CONFIG_SCSI_U14_34F is not set
+# CONFIG_SCSI_NSP32 is not set
 # CONFIG_SCSI_DEBUG is not set
 
 #
@@ -335,6 +353,7 @@
 # CONFIG_NS83820 is not set
 # CONFIG_HAMACHI is not set
 # CONFIG_YELLOWFIN is not set
+# CONFIG_R8169 is not set
 # CONFIG_SK98LIN is not set
 # CONFIG_TIGON3 is not set
 # CONFIG_FDDI is not set
@@ -389,10 +408,35 @@
 # Character devices
 #
 # CONFIG_VT is not set
-CONFIG_SERIAL=y
-CONFIG_SERIAL_CONSOLE=y
+# CONFIG_SERIAL is not set
 # CONFIG_SERIAL_EXTENDED is not set
-# CONFIG_SERIAL_NONSTANDARD is not set
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_COMPUTONE is not set
+# CONFIG_ROCKETPORT is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_DIGIEPCA is not set
+# CONFIG_DIGI is not set
+# CONFIG_ESPSERIAL is not set
+# CONFIG_MOXA_INTELLIO is not set
+# CONFIG_MOXA_SMARTIO is not set
+# CONFIG_ISI is not set
+# CONFIG_SYNCLINK is not set
+# CONFIG_SYNCLINKMP is not set
+# CONFIG_N_HDLC is not set
+# CONFIG_RISCOM8 is not set
+# CONFIG_SPECIALIX is not set
+# CONFIG_SX is not set
+# CONFIG_RIO is not set
+# CONFIG_STALDRV is not set
+# CONFIG_SERIAL_TX3912 is not set
+# CONFIG_SERIAL_TX3912_CONSOLE is not set
+# CONFIG_SERIAL_TXX9 is not set
+# CONFIG_SERIAL_TXX9_CONSOLE is not set
+# CONFIG_TXX927_SERIAL is not set
+CONFIG_SERIAL_DEC=y
+CONFIG_SERIAL_DEC_CONSOLE=y
+CONFIG_DZ=y
+CONFIG_ZS=y
 CONFIG_UNIX98_PTYS=y
 CONFIG_UNIX98_PTY_COUNT=256
 
@@ -420,13 +464,21 @@
 # Input core support is needed for joysticks
 #
 # CONFIG_QIC02_TAPE is not set
+# CONFIG_IPMI_HANDLER is not set
+# CONFIG_IPMI_PANIC_EVENT is not set
+# CONFIG_IPMI_DEVICE_INTERFACE is not set
+# CONFIG_IPMI_KCS is not set
+# CONFIG_IPMI_WATCHDOG is not set
 
 #
 # Watchdog Cards
 #
 # CONFIG_WATCHDOG is not set
+# CONFIG_SCx200_GPIO is not set
+# CONFIG_AMD_PM768 is not set
 # CONFIG_NVRAM is not set
 # CONFIG_RTC is not set
+# CONFIG_MIPS_RTC is not set
 # CONFIG_DTLK is not set
 # CONFIG_R3964 is not set
 # CONFIG_APPLICOM is not set
@@ -439,18 +491,10 @@
 # CONFIG_DRM is not set
 
 #
-# DECStation Character devices
-#
-CONFIG_SERIAL=y
-# CONFIG_DZ is not set
-CONFIG_ZS=y
-CONFIG_SERIAL_CONSOLE=y
-# CONFIG_RTC is not set
-
-#
 # File systems
 #
 # CONFIG_QUOTA is not set
+# CONFIG_QFMT_V2 is not set
 # CONFIG_AUTOFS_FS is not set
 # CONFIG_AUTOFS4_FS is not set
 # CONFIG_REISERFS_FS is not set
@@ -460,6 +504,7 @@
 # CONFIG_ADFS_FS_RW 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_BEFS_DEBUG is not set
 # CONFIG_BFS_FS is not set
@@ -509,6 +554,7 @@
 # CONFIG_INTERMEZZO_FS is not set
 # CONFIG_NFS_FS is not set
 # CONFIG_NFS_V3 is not set
+# CONFIG_NFS_DIRECTIO is not set
 # CONFIG_ROOT_NFS is not set
 # CONFIG_NFSD is not set
 # CONFIG_NFSD_V3 is not set
@@ -573,14 +619,20 @@
 # Kernel hacking
 #
 CONFIG_CROSSCOMPILE=y
-# CONFIG_REMOTE_DEBUG is not set
+# CONFIG_RUNTIME_DEBUG is not set
+# CONFIG_KGDB is not set
 # CONFIG_GDB_CONSOLE is not set
-# CONFIG_DEBUG is not set
 # CONFIG_MAGIC_SYSRQ is not set
 # CONFIG_MIPS_UNCACHED is not set
 
 #
+# Cryptographic options
+#
+# CONFIG_CRYPTO is not set
+
+#
 # Library routines
 #
+# CONFIG_CRC32 is not set
 # CONFIG_ZLIB_INFLATE is not set
 # CONFIG_ZLIB_DEFLATE is not set
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/ecc.h linux-2.4.21-bk34/include/asm-mips/dec/ecc.h
--- linux-2.4.21-bk33/include/asm-mips/dec/ecc.h	1969-12-31 16:00:00.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/ecc.h	2003-08-15 02:54:50.000000000 -0700
@@ -0,0 +1,51 @@
+/*
+ *	include/asm-mips/dec/ecc.h
+ *
+ *	ECC handling logic definitions common to DECstation/DECsystem
+ *	5000/200 (KN02), 5000/240 (KN03), 5000/260 (KN05) and
+ *	DECsystem 5900 (KN03), 5900/260 (KN05) systems.
+ *
+ *	Copyright (C) 2003  Maciej W. Rozycki
+ *
+ *	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.
+ */
+#ifndef __ASM_MIPS_DEC_ECC_H
+#define __ASM_MIPS_DEC_ECC_H
+
+/*
+ * Error Address Register bits.
+ * The register is r/wc -- any write clears it.
+ */
+#define KN0X_EAR_VALID		(1<<31)		/* error data valid, bus IRQ */
+#define KN0X_EAR_CPU		(1<<30)		/* CPU/DMA transaction */
+#define KN0X_EAR_WRITE		(1<<29)		/* write/read transaction */
+#define KN0X_EAR_ECCERR		(1<<28)		/* ECC/timeout or overrun */
+#define KN0X_EAR_RES_27		(1<<27)		/* unused */
+#define KN0X_EAR_ADDRESS	(0x7ffffff<<0)	/* address involved */
+
+/*
+ * Error Syndrome Register bits.
+ * The register is frozen when EAR.VALID is set, otherwise it records bits
+ * from the last memory read.  The register is r/wc -- any write clears it.
+ */
+#define KN0X_ESR_VLDHI		(1<<31)		/* error data valid hi word */
+#define KN0X_ESR_CHKHI		(0x7f<<24)	/* check bits read from mem */
+#define KN0X_ESR_SNGHI		(1<<23)		/* single/double bit error */
+#define KN0X_ESR_SYNHI		(0x7f<<16)	/* syndrome from ECC logic */
+#define KN0X_ESR_VLDLO		(1<<15)		/* error data valid lo word */
+#define KN0X_ESR_CHKLO		(0x7f<<8)	/* check bits read from mem */
+#define KN0X_ESR_SNGLO		(1<<7)		/* single/double bit error */
+#define KN0X_ESR_SYNLO		(0x7f<<0)	/* syndrome from ECC logic */
+
+
+#ifndef __ASSEMBLY__
+struct pt_regs;
+extern void dec_ecc_be_init(void);
+extern int dec_ecc_be_handler(struct pt_regs *regs, int is_fixup);
+extern void dec_ecc_be_interrupt(int irq, void *dev_id, struct pt_regs *regs);
+#endif
+
+#endif /* __ASM_MIPS_DEC_ECC_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/interrupts.h linux-2.4.21-bk34/include/asm-mips/dec/interrupts.h
--- linux-2.4.21-bk33/include/asm-mips/dec/interrupts.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/interrupts.h	2003-08-15 02:54:50.000000000 -0700
@@ -8,7 +8,7 @@
  *
  * Copyright (C) 1997 by Paul M. Antoine.
  * reworked 1998 by Harald Koerfgen.
- * Copyright (C) 2001, 2002  Maciej W. Rozycki
+ * Copyright (C) 2001, 2002, 2003  Maciej W. Rozycki
  */
 
 #ifndef __ASM_DEC_INTERRUPTS_H
@@ -33,7 +33,7 @@
 #define DEC_IRQ_HALT		7	/* HALT button or from ACCESS.Bus */
 #define DEC_IRQ_ISDN		8	/* Am79C30A ISDN */
 #define DEC_IRQ_LANCE		9	/* LANCE (Am7990) Ethernet */
-#define DEC_IRQ_MEMORY		10	/* memory, I/O bus write errors */
+#define DEC_IRQ_BUS		10	/* memory, I/O bus read/write errors */
 #define DEC_IRQ_PSU		11	/* power supply unit warning */
 #define DEC_IRQ_RTC		12	/* DS1287 RTC */
 #define DEC_IRQ_SCC0		13	/* SCC (Z85C30) serial #0 */
@@ -58,10 +58,10 @@
 #define DEC_IRQ_SCC0A_RXDMA	30	/* SCC0A receive half page */
 #define DEC_IRQ_SCC0A_TXERR	31	/* SCC0A xmit memory read/overrun */
 #define DEC_IRQ_SCC0A_TXDMA	32	/* SCC0A transmit page end */
-#define DEC_IRQ_SCC0B_RXERR	33	/* SCC0B (ACCESS.bus) receive overrun */
-#define DEC_IRQ_SCC0B_RXDMA	34	/* SCC0B receive half page */
-#define DEC_IRQ_SCC0B_TXERR	35	/* SCC0B xmit memory read/overrun */
-#define DEC_IRQ_SCC0B_TXDMA	36	/* SCC0B transmit page end */
+#define DEC_IRQ_AB_RXERR	33	/* ACCESS.bus receive overrun */
+#define DEC_IRQ_AB_RXDMA	34	/* ACCESS.bus receive half page */
+#define DEC_IRQ_AB_TXERR	35	/* ACCESS.bus xmit memory read/ovrn */
+#define DEC_IRQ_AB_TXDMA	36	/* ACCESS.bus transmit page end */
 #define DEC_IRQ_SCC1A_RXERR	37	/* SCC1A (modem) receive overrun */
 #define DEC_IRQ_SCC1A_RXDMA	38	/* SCC1A receive half page */
 #define DEC_IRQ_SCC1A_TXERR	39	/* SCC1A xmit memory read/overrun */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/ioasic.h linux-2.4.21-bk34/include/asm-mips/dec/ioasic.h
--- linux-2.4.21-bk33/include/asm-mips/dec/ioasic.h	2002-08-02 17:39:45.000000000 -0700
+++ linux-2.4.21-bk34/include/asm-mips/dec/ioasic.h	2003-08-15 02:54:50.000000000 -0700
@@ -3,7 +3,7 @@
  *
  *	DEC I/O ASIC access operations.
  *
- *	Copyright (C) 2000, 2002  Maciej W. Rozycki
+ *	Copyright (C) 2000, 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -14,8 +14,11 @@
 #ifndef __ASM_DEC_IOASIC_H
 #define __ASM_DEC_IOASIC_H
 
+#include <linux/spinlock.h>
 #include <linux/types.h>
 
+extern spinlock_t ioasic_ssr_lock;
+
 extern volatile u32 *ioasic_base;
 
 static inline void ioasic_write(unsigned int reg, u32 v)
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/ioasic_addrs.h linux-2.4.21-bk34/include/asm-mips/dec/ioasic_addrs.h
--- linux-2.4.21-bk33/include/asm-mips/dec/ioasic_addrs.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/ioasic_addrs.h	2003-08-15 02:54:50.000000000 -0700
@@ -10,74 +10,142 @@
  * "DEC 3000 300/400/500/600/700/800/900 AXP Models System Programmer's Manual"
  *
  * and the Mach Sources
+ *
+ * Copyright (C) 199x  the Anonymous
+ * Copyright (C) 2002, 2003  Maciej W. Rozycki
  */
 
-#ifndef IOASIC_ADDRS_H
-#define IOASIC_ADDRS_H
+#ifndef __ASM_MIPS_DEC_IOASIC_ADDRS_H
+#define __ASM_MIPS_DEC_IOASIC_ADDRS_H
 
 #define IOASIC_SLOT_SIZE 0x00040000
 
-#define SYSTEM_ROM 	(0*IOASIC_SLOT_SIZE)	/* board ROM */
-#define IOCTL 		(1*IOASIC_SLOT_SIZE)	/* I/O ASIC */
-#define ESAR 		(2*IOASIC_SLOT_SIZE)	/* LANCE MAC address chip */
-#define LANCE 		(3*IOASIC_SLOT_SIZE)	/* LANCE Ethernet */
-#define SCC0 		(4*IOASIC_SLOT_SIZE)	/* SCC #0 */
-#define VDAC_HI		(5*IOASIC_SLOT_SIZE)	/* VDAC (maxine) */
-#define SCC1 		(6*IOASIC_SLOT_SIZE)	/* SCC #1 (3min, 3max+) */
-#define VDAC_LO		(7*IOASIC_SLOT_SIZE)	/* VDAC (maxine) */
-#define TOY 		(8*IOASIC_SLOT_SIZE)	/* RTC */
-#define ISDN 		(9*IOASIC_SLOT_SIZE)	/* ISDN (maxine) */
-#define ERRADDR		(9*IOASIC_SLOT_SIZE)	/* bus error address (3max+) */
-#define CHKSYN 		(10*IOASIC_SLOT_SIZE)	/* ECC syndrome (3max+) */
-#define ACCESS_BUS	(10*IOASIC_SLOT_SIZE)	/* Access.Bus (maxine) */
-#define MCR 		(11*IOASIC_SLOT_SIZE)	/* memory control (3max+) */
-#define FLOPPY 		(11*IOASIC_SLOT_SIZE)	/* FDC (maxine) */
-#define SCSI 		(12*IOASIC_SLOT_SIZE)	/* ASC SCSI */
-#define FLOPPY_DMA 	(13*IOASIC_SLOT_SIZE)	/* FDC DMA (maxine) */
-#define SCSI_DMA 	(14*IOASIC_SLOT_SIZE)	/* ??? */
-#define RESERVED_4 	(15*IOASIC_SLOT_SIZE)	/* unused? */
+/*
+ * Address ranges decoded by the I/O ASIC for onboard devices.
+ */
+#define IOASIC_SYS_ROM	(0*IOASIC_SLOT_SIZE)	/* system board ROM */
+#define IOASIC_IOCTL	(1*IOASIC_SLOT_SIZE)	/* I/O ASIC */
+#define IOASIC_ESAR 	(2*IOASIC_SLOT_SIZE)	/* LANCE MAC address chip */
+#define IOASIC_LANCE 	(3*IOASIC_SLOT_SIZE)	/* LANCE Ethernet */
+#define IOASIC_SCC0 	(4*IOASIC_SLOT_SIZE)	/* SCC #0 */
+#define IOASIC_VDAC_HI	(5*IOASIC_SLOT_SIZE)	/* VDAC (maxine) */
+#define IOASIC_SCC1 	(6*IOASIC_SLOT_SIZE)	/* SCC #1 (3min, 3max+) */
+#define IOASIC_VDAC_LO	(7*IOASIC_SLOT_SIZE)	/* VDAC (maxine) */
+#define IOASIC_TOY 	(8*IOASIC_SLOT_SIZE)	/* RTC */
+#define IOASIC_ISDN 	(9*IOASIC_SLOT_SIZE)	/* ISDN (maxine) */
+#define IOASIC_ERRADDR	(9*IOASIC_SLOT_SIZE)	/* bus error address (3max+) */
+#define IOASIC_CHKSYN 	(10*IOASIC_SLOT_SIZE)	/* ECC syndrome (3max+) */
+#define IOASIC_ACC_BUS	(10*IOASIC_SLOT_SIZE)	/* ACCESS.bus (maxine) */
+#define IOASIC_MCR 	(11*IOASIC_SLOT_SIZE)	/* memory control (3max+) */
+#define IOASIC_FLOPPY 	(11*IOASIC_SLOT_SIZE)	/* FDC (maxine) */
+#define IOASIC_SCSI 	(12*IOASIC_SLOT_SIZE)	/* ASC SCSI */
+#define IOASIC_FDC_DMA	(13*IOASIC_SLOT_SIZE)	/* FDC DMA (maxine) */
+#define IOASIC_SCSI_DMA	(14*IOASIC_SLOT_SIZE)	/* ??? */
+#define IOASIC_RES_15	(15*IOASIC_SLOT_SIZE)	/* unused? */
+
 
 /*
- * Offsets for IOCTL registers (relative to (system_base + IOCTL))
+ * Offsets for I/O ASIC registers (relative to (system_base + IOASIC_IOCTL)).
  */
-#define SCSI_DMA_P	0x00			/* SCSI DMA Pointer */
-#define SCSI_DMA_BP	0x10			/* SCSI DMA Buffer Pointer */
-#define LANCE_DMA_P	0x20			/* LANCE DMA Pointer */
-#define SCC0_T_DMA_P	0x30			/* Communication Port 1 Transmit DMA Pointer */
-#define SCC0_R_DMA_P	0x40			/* Communication Port 1 Receive DMA Pointer */
-#define SCC1_T_DMA_P	0x50			/* Communication Port 2 Transmit DMA Pointer */
-#define SCC1_R_DMA_P	0x60			/* Communication Port 2 Receive DMA Pointer */
-#define FLOPPY_DMA_P	0x70			/* Floppy DMA Pointer */
-#define ISDN_T_DMA_P	0x80			/* ISDN Transmit DMA Pointer */
-#define ISDN_T_DMA_BP	0x90			/* ISDN Transmit DMA Buffer Pointer */
-#define ISDN_R_DMA_P	0xa0			/* ISDN Receive DMA Pointer */
-#define ISDN_R_DMA_BP	0xb0			/* ISDN Receive DMA Buffer Pointer */
-
-#define SSR		0x100			/* System Support Register */
-#define SIR		0x110			/* System Interrupt Register */
-#define SIMR		0x120			/* System Interrupt Mask Register */
-#define FCTR		0x1e0			/* Free-Running Counter */
+					/* all systems */
+#define IO_REG_SCSI_DMA_P	0x00	/* SCSI DMA Pointer */
+#define IO_REG_SCSI_DMA_BP	0x10	/* SCSI DMA Buffer Pointer */
+#define IO_REG_LANCE_DMA_P	0x20	/* LANCE DMA Pointer */
+#define IO_REG_SCC0A_T_DMA_P	0x30	/* SCC0A Transmit DMA Pointer */
+#define IO_REG_SCC0A_R_DMA_P	0x40	/* SCC0A Receive DMA Pointer */
+
+					/* except Maxine */
+#define IO_REG_SCC1A_T_DMA_P	0x50	/* SCC1A Transmit DMA Pointer */
+#define IO_REG_SCC1A_R_DMA_P	0x60	/* SCC1A Receive DMA Pointer */
+
+					/* Maxine */
+#define IO_REG_AB_T_DMA_P	0x50	/* ACCESS.bus Transmit DMA Pointer */
+#define IO_REG_AB_R_DMA_P	0x60	/* ACCESS.bus Receive DMA Pointer */
+#define IO_REG_FLOPPY_DMA_P	0x70	/* Floppy DMA Pointer */
+#define IO_REG_ISDN_T_DMA_P	0x80	/* ISDN Transmit DMA Pointer */
+#define IO_REG_ISDN_T_DMA_BP	0x90	/* ISDN Transmit DMA Buffer Pointer */
+#define IO_REG_ISDN_R_DMA_P	0xa0	/* ISDN Receive DMA Pointer */
+#define IO_REG_ISDN_R_DMA_BP	0xb0	/* ISDN Receive DMA Buffer Pointer */
+
+					/* all systems */
+#define IO_REG_DATA_0		0xc0	/* System Data Buffer 0 */
+#define IO_REG_DATA_1		0xd0	/* System Data Buffer 1 */
+#define IO_REG_DATA_2		0xe0	/* System Data Buffer 2 */
+#define IO_REG_DATA_3		0xf0	/* System Data Buffer 3 */
+
+					/* all systems */
+#define IO_REG_SSR		0x100	/* System Support Register */
+#define IO_REG_SIR		0x110	/* System Interrupt Register */
+#define IO_REG_SIMR		0x120	/* System Interrupt Mask Reg. */
+#define IO_REG_SAR		0x130	/* System Address Register */
+
+					/* Maxine */
+#define IO_REG_ISDN_T_DATA	0x140	/* ISDN Xmit Data Register */
+#define IO_REG_ISDN_R_DATA	0x150	/* ISDN Receive Data Register */
+
+					/* all systems */
+#define IO_REG_LANCE_SLOT	0x160	/* LANCE I/O Slot Register */
+#define IO_REG_SCSI_SLOT	0x170	/* SCSI Slot Register */
+#define IO_REG_SCC0A_SLOT	0x180	/* SCC0A DMA Slot Register */
+
+					/* except Maxine */
+#define IO_REG_SCC1A_SLOT	0x190	/* SCC1A DMA Slot Register */
+
+					/* Maxine */
+#define IO_REG_AB_SLOT		0x190	/* ACCESS.bus DMA Slot Register */
+#define IO_REG_FLOPPY_SLOT	0x1a0	/* Floppy Slot Register */
+
+					/* all systems */
+#define IO_REG_SCSI_SCR		0x1b0	/* SCSI Partial-Word DMA Control */
+#define IO_REG_SCSI_SDR0	0x1c0	/* SCSI DMA Partial Word 0 */
+#define IO_REG_SCSI_SDR1	0x1d0	/* SCSI DMA Partial Word 1 */
+#define IO_REG_FCTR		0x1e0	/* Free-Running Counter */
+#define IO_REG_RES_31		0x1f0	/* unused */
+
 
 /*
- * Handle partial word SCSI DMA transfers
+ * The upper 16 bits of the System Support Register are a part of the
+ * I/O ASIC's internal DMA engine and thus are common to all I/O ASIC
+ * machines.  The exception is the Maxine, which makes use of the
+ * FLOPPY and ISDN bits (otherwise unused) and has a different SCC
+ * wiring.
  */
-#define	SCSI_SCR	0x1b0
-#define	SCSI_SDR0	0x1c0
-#define	SCSI_SDR1	0x1d0
+						/* all systems */
+#define IO_SSR_SCC0A_TX_DMA_EN	(1<<31)		/* SCC0A transmit DMA enable */
+#define IO_SSR_SCC0A_RX_DMA_EN	(1<<30)		/* SCC0A receive DMA enable */
+#define IO_SSR_RES_27		(1<<27)		/* unused */
+#define IO_SSR_RES_26		(1<<26)		/* unused */
+#define IO_SSR_RES_25		(1<<25)		/* unused */
+#define IO_SSR_RES_24		(1<<24)		/* unused */
+#define IO_SSR_RES_23		(1<<23)		/* unused */
+#define IO_SSR_SCSI_DMA_DIR	(1<<18)		/* SCSI DMA direction */
+#define IO_SSR_SCSI_DMA_EN	(1<<17)		/* SCSI DMA enable */
+#define IO_SSR_LANCE_DMA_EN	(1<<16)		/* LANCE DMA enable */
+
+						/* except Maxine */
+#define IO_SSR_SCC1A_TX_DMA_EN	(1<<29)		/* SCC1A transmit DMA enable */
+#define IO_SSR_SCC1A_RX_DMA_EN	(1<<28)		/* SCC1A receive DMA enable */
+#define IO_SSR_RES_22		(1<<22)		/* unused */
+#define IO_SSR_RES_21		(1<<21)		/* unused */
+#define IO_SSR_RES_20		(1<<20)		/* unused */
+#define IO_SSR_RES_19		(1<<19)		/* unused */
+
+						/* Maxine */
+#define IO_SSR_AB_TX_DMA_EN	(1<<29)		/* ACCESS.bus xmit DMA enable */
+#define IO_SSR_AB_RX_DMA_EN	(1<<28)		/* ACCESS.bus recv DMA enable */
+#define IO_SSR_FLOPPY_DMA_DIR	(1<<22)		/* Floppy DMA direction */
+#define IO_SSR_FLOPPY_DMA_EN	(1<<21)		/* Floppy DMA enable */
+#define IO_SSR_ISDN_TX_DMA_EN	(1<<20)		/* ISDN transmit DMA enable */
+#define IO_SSR_ISDN_RX_DMA_EN	(1<<19)		/* ISDN receive DMA enable */
 
 /*
- * DMA defines for the System Support Register
+ * The lower 16 bits are system-specific.  Bits 15,11:8 are common and
+ * defined here.  The rest is defined in system-specific headers.
  */
-#define LANCE_DMA_EN	(1UL<<16)			/* LANCE DMA enable */
-#define SCSI_DMA_EN	(1UL<<17)			/* SCSI DMA enable */
-#define SCSI_DMA_DIR	(1UL<<18)			/* SCSI DMA direction */
-#define ISDN_REC_DMA_EN (1UL<<19)			/* ISDN receive DMA enable */
-#define ISDN_TRN_DMA_EN (1UL<<20)			/* ISDN transmit DMA enable */
-#define FLOPPY_DMA_EN	(1UL<<21)			/* Floppy DMA enable */
-#define FLOPPY_DMA_DIR	(1UL<<22)			/* Floppy DMA direction */
-#define SCC1A_DMA_EN	(1UL<<28)			/* SCC1 Channel A DMA enable */
-#define SCC1B_DMA_EN	(1UL<<29)			/* SCC1 Channel B DMA enable */
-#define SCC0A_DMA_EN	(1UL<<30)			/* SCC0 Channel A DMA enable */
-#define SCC0B_DMA_EN	(1UL<<31)			/* Scc0 Channel B DMA enable */
+#define KN0X_IO_SSR_DIAGDN	(1<<15)		/* diagnostic jumper */
+#define KN0X_IO_SSR_SCC_RST	(1<<11)		/* ~SCC0,1 (Z85C30) reset */
+#define KN0X_IO_SSR_RTC_RST	(1<<10)		/* ~RTC (DS1287) reset */
+#define KN0X_IO_SSR_ASC_RST	(1<<9)		/* ~ASC (NCR53C94) reset */
+#define KN0X_IO_SSR_LANCE_RST	(1<<8)		/* ~LANCE (Am7990) reset */
 
-#endif
+#endif /* __ASM_MIPS_DEC_IOASIC_ADDRS_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/ioasic_ints.h linux-2.4.21-bk34/include/asm-mips/dec/ioasic_ints.h
--- linux-2.4.21-bk33/include/asm-mips/dec/ioasic_ints.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/ioasic_ints.h	2003-08-15 02:54:50.000000000 -0700
@@ -46,10 +46,10 @@
 #define IO_INR_RES_20		20	/* unused */
 
 					/* Maxine */
-#define IO_INR_SCC0B_TXDMA	27	/* SCC0B transmit page end */
-#define IO_INR_SCC0B_TXERR	26	/* SCC0B transmit memory read error */
-#define IO_INR_SCC0B_RXDMA	25	/* SCC0B receive half page */
-#define IO_INR_SCC0B_RXERR	24	/* SCC0B receive overrun */
+#define IO_INR_AB_TXDMA		27	/* ACCESS.bus transmit page end */
+#define IO_INR_AB_TXERR		26	/* ACCESS.bus xmit memory read error */
+#define IO_INR_AB_RXDMA		25	/* ACCESS.bus receive half page */
+#define IO_INR_AB_RXERR		24	/* ACCESS.bus receive overrun */
 #define IO_INR_FLOPPY_ERR	23	/* FDC error */
 #define IO_INR_ISDN_TXDMA	22	/* ISDN xmit buffer pointer loaded */
 #define IO_INR_ISDN_RXDMA	21	/* ISDN recv buffer pointer loaded */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn01.h linux-2.4.21-bk34/include/asm-mips/dec/kn01.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn01.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn01.h	2003-08-15 02:54:50.000000000 -0700
@@ -8,31 +8,76 @@
  *
  * Copyright (C) 1995,1996 by Paul M. Antoine, some code and definitions
  * are by courtesy of Chris Fraser.
- * Copyright (C) 2002  Maciej W. Rozycki
+ * Copyright (C) 2002, 2003  Maciej W. Rozycki
  */
 #ifndef __ASM_MIPS_DEC_KN01_H
 #define __ASM_MIPS_DEC_KN01_H
 
 #include <asm/addrspace.h>
 
+#define KN01_SLOT_BASE	KSEG1ADDR(0x10000000)
+#define KN01_SLOT_SIZE	0x01000000
+
+/*
+ * Address ranges for devices.
+ */
+#define KN01_PMASK	(0*KN01_SLOT_SIZE)	/* color plane mask */
+#define KN01_PCC	(1*KN01_SLOT_SIZE)	/* PCC (DC503) cursor */
+#define KN01_VDAC	(2*KN01_SLOT_SIZE)	/* color map */
+#define KN01_RES_3	(3*KN01_SLOT_SIZE)	/* unused */
+#define KN01_RES_4	(4*KN01_SLOT_SIZE)	/* unused */
+#define KN01_RES_5	(5*KN01_SLOT_SIZE)	/* unused */
+#define KN01_RES_6	(6*KN01_SLOT_SIZE)	/* unused */
+#define KN01_ERRADDR	(7*KN01_SLOT_SIZE)	/* write error address */
+#define KN01_LANCE	(8*KN01_SLOT_SIZE)	/* LANCE (Am7990) Ethernet */
+#define KN01_LANCE_MEM	(9*KN01_SLOT_SIZE)	/* LANCE buffer memory */
+#define KN01_SII	(10*KN01_SLOT_SIZE)	/* SII (DC7061) SCSI */
+#define KN01_SII_MEM	(11*KN01_SLOT_SIZE)	/* SII buffer memory */
+#define KN01_DZ11	(12*KN01_SLOT_SIZE)	/* DZ11 (DC7085) serial */
+#define KN01_RTC	(13*KN01_SLOT_SIZE)	/* DS1287 RTC (bytes #0) */
+#define KN01_ESAR	(13*KN01_SLOT_SIZE)	/* MAC address (bytes #1) */
+#define KN01_CSR	(14*KN01_SLOT_SIZE)	/* system ctrl & status reg */
+#define KN01_SYS_ROM	(15*KN01_SLOT_SIZE)	/* system board ROM */
+
+
 /*
  * Some port addresses...
  */
-#define KN01_SLOT_SIZE	0x01000000
+#define KN01_LANCE_BASE (KN01_SLOT_BASE + KN01_LANCE)	/* 0xB8000000 */
+#define KN01_DZ11_BASE	(KN01_SLOT_BASE + KN01_DZ11)	/* 0xBC000000 */
+#define KN01_RTC_BASE	(KN01_SLOT_BASE + KN01_RTC)	/* 0xBD000000 */
 
-#define KN01_LANCE_BASE (KSEG1ADDR(0x18000000)) /* 0xB8000000 */
-#define KN01_DZ11_BASE	(KSEG1ADDR(0x1c000000)) /* 0xBC000000 */
-#define KN01_RTC_BASE	(KSEG1ADDR(0x1d000000)) /* 0xBD000000 */
 
+/*
+ * Frame buffer memory address.
+ */
+#define KN01_VFB_MEM	KSEG1ADDR(0x0fc00000)
 
 /*
  * CPU interrupt bits.
  */
-#define KN01_CPU_INR_MEMORY	6	/* memory, I/O bus write errors */
-#define KN01_CPU_INR_VIDEO	6	/* framebuffer */
+#define KN01_CPU_INR_BUS	6	/* memory, I/O bus read/write errors */
+#define KN01_CPU_INR_VIDEO	6	/* PCC area detect #2 */
 #define KN01_CPU_INR_RTC	5	/* DS1287 RTC */
 #define KN01_CPU_INR_DZ11	4	/* DZ11 (DC7085) serial */
 #define KN01_CPU_INR_LANCE	3	/* LANCE (Am7990) Ethernet */
 #define KN01_CPU_INR_SII	2	/* SII (DC7061) SCSI */
 
+
+/*
+ * System Control & Status Register bits.
+ */
+#define KN01_CSR_MNFMOD		(1<<15)	/* MNFMOD manufacturing jumper */
+#define KN01_CSR_STATUS		(1<<14)	/* self-test result status output */
+#define KN01_CSR_PARDIS		(1<<13)	/* parity error disable */
+#define KN01_CSR_CRSRTST	(1<<12)	/* PCC test output */
+#define KN01_CSR_MONO		(1<<11)	/* mono/color fb SIMM installed */
+#define KN01_CSR_MEMERR		(1<<10)	/* write timeout error status & ack*/
+#define KN01_CSR_VINT		(1<<9)	/* PCC area detect #2 status & ack */
+#define KN01_CSR_TXDIS		(1<<8)	/* DZ11 transmit disable */
+#define KN01_CSR_VBGTRG		(1<<2)	/* blue DAC voltage over green (r/o) */
+#define KN01_CSR_VRGTRG		(1<<1)	/* red DAC voltage over green (r/o) */
+#define KN01_CSR_VRGTRB		(1<<0)	/* red DAC voltage over blue (r/o) */
+#define KN01_CSR_LEDS		(0xff<<0) /* ~diagnostic LEDs (w/o) */
+
 #endif /* __ASM_MIPS_DEC_KN01_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn02.h linux-2.4.21-bk34/include/asm-mips/dec/kn02.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn02.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn02.h	2003-08-15 02:54:50.000000000 -0700
@@ -8,7 +8,7 @@
  *
  * Copyright (C) 1995,1996 by Paul M. Antoine, some code and definitions
  * are by courtesy of Chris Fraser.
- * Copyright (C) 2002  Maciej W. Rozycki
+ * Copyright (C) 2002, 2003  Maciej W. Rozycki
  */
 #ifndef __ASM_MIPS_DEC_KN02_H
 #define __ASM_MIPS_DEC_KN02_H
@@ -19,29 +19,59 @@
 #endif
 
 #include <asm/addrspace.h>
+#include <asm/dec/ecc.h>
 
 
+#define KN02_SLOT_BASE	KSEG1ADDR(0x1fc00000)
+#define KN02_SLOT_SIZE	0x00080000
+
 /*
- * Motherboard regs (kseg1 addresses)
+ * Address ranges decoded by the "system slot" logic for onboard devices.
  */
-#define KN02_CSR_ADDR	KSEG1ADDR(0x1ff00000)	/* system control & status reg */
+#define KN02_SYS_ROM	(0*KN02_SLOT_SIZE)	/* system board ROM */
+#define KN02_RES_1	(1*KN02_SLOT_SIZE)	/* unused */
+#define KN02_CHKSYN	(2*KN02_SLOT_SIZE)	/* ECC syndrome */
+#define KN02_ERRADDR	(3*KN02_SLOT_SIZE)	/* bus error address */
+#define KN02_DZ11	(4*KN02_SLOT_SIZE)	/* DZ11 (DC7085) serial */
+#define KN02_RTC	(5*KN02_SLOT_SIZE)	/* DS1287 RTC */
+#define KN02_CSR	(6*KN02_SLOT_SIZE)	/* system ctrl & status reg */
+#define KN02_SYS_ROM_7	(7*KN02_SLOT_SIZE)	/* system board ROM (alias) */
+
 
 /*
  * Some port addresses...
  */
-#define KN02_SLOT_SIZE	0x00080000
+#define KN02_DZ11_BASE	(KN02_SLOT_BASE + KN02_DZ11)	/* DZ11 */
+#define KN02_RTC_BASE	(KN02_SLOT_BASE + KN02_RTC)	/* RTC */
+#define KN02_CSR_BASE	(KN02_SLOT_BASE + KN02_CSR)	/* CSR */
 
-#define KN02_RTC_BASE	KSEG1ADDR(0x1fe80000)
-#define KN02_DZ11_BASE	KSEG1ADDR(0x1fe00000)
 
-#define KN02_CSR_BNK32M	(1<<10)			/* 32M stride */
+/*
+ * System Control & Status Register bits.
+ */
+#define KN02_CSR_RES_28		(0xf<<28)	/* unused */
+#define KN02_CSR_PSU		(1<<27)		/* power supply unit warning */
+#define KN02_CSR_NVRAM		(1<<26)		/* ~NVRAM clear jumper */
+#define KN02_CSR_REFEVEN	(1<<25)		/* mem refresh bank toggle */
+#define KN03_CSR_NRMOD		(1<<24)		/* ~NRMOD manufact. jumper */
+#define KN03_CSR_IOINTEN	(0xff<<16)	/* IRQ mask bits */
+#define KN02_CSR_DIAGCHK	(1<<15)		/* diagn/norml ECC reads */
+#define KN02_CSR_DIAGGEN	(1<<14)		/* diagn/norml ECC writes */
+#define KN02_CSR_CORRECT	(1<<13)		/* ECC correct/check */
+#define KN02_CSR_LEDIAG		(1<<12)		/* ECC diagn. latch strobe */
+#define KN02_CSR_TXDIS		(1<<11)		/* DZ11 transmit disable */
+#define KN02_CSR_BNK32M		(1<<10)		/* 32M/8M stride */
+#define KN02_CSR_DIAGDN		(1<<9)		/* DIAGDN manufact. jumper */
+#define KN02_CSR_BAUD38		(1<<8)		/* DZ11 38/19kbps ext. rate */
+#define KN03_CSR_IOINT		(0xff<<0)	/* IRQ status bits (r/o) */
+#define KN03_CSR_LEDS		(0xff<<0)	/* ~diagnostic LEDs (w/o) */
 
 
 /*
  * CPU interrupt bits.
  */
 #define KN02_CPU_INR_RES_6	6	/* unused */
-#define KN02_CPU_INR_MEMORY	5	/* memory, I/O bus write errors */
+#define KN02_CPU_INR_BUS	5	/* memory, I/O bus read/write errors */
 #define KN02_CPU_INR_RES_4	4	/* unused */
 #define KN02_CPU_INR_RTC	3	/* DS1287 RTC */
 #define KN02_CPU_INR_CASCADE	2	/* CSR cascade */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn02ba.h linux-2.4.21-bk34/include/asm-mips/dec/kn02ba.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn02ba.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn02ba.h	2003-08-15 02:54:50.000000000 -0700
@@ -3,7 +3,7 @@
  *
  *	DECstation 5000/1xx (3min or KN02-BA) definitions.
  *
- *	Copyright (C) 2002  Maciej W. Rozycki
+ *	Copyright (C) 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -16,12 +16,6 @@
 #include <asm/dec/kn02xa.h>		/* For common definitions. */
 
 /*
- * Some port addresses...
- */
-#define KN02BA_IOASIC_BASE	KN02XA_IOASIC_BASE	/* I/O ASIC */
-#define KN02BA_RTC_BASE		KN02XA_RTC_BASE		/* RTC */
-
-/*
  * CPU interrupt bits.
  */
 #define KN02BA_CPU_INR_HALT	6	/* HALT button */
@@ -36,7 +30,7 @@
 #define KN02BA_IO_INR_RES_15	15	/* unused */
 #define KN02BA_IO_INR_NVRAM	14	/* (*) NVRAM clear jumper */
 #define KN02BA_IO_INR_RES_13	13	/* unused */
-#define KN02BA_IO_INR_MEMORY	12	/* memory, I/O bus write errors */
+#define KN02BA_IO_INR_BUS	12	/* memory, I/O bus read/write errors */
 #define KN02BA_IO_INR_RES_11	11	/* unused */
 #define KN02BA_IO_INR_NRMOD	10	/* (*) NRMOD manufacturing jumper */
 #define KN02BA_IO_INR_ASC	9	/* ASC (NCR53C94) SCSI */
@@ -46,8 +40,28 @@
 #define KN02BA_IO_INR_RTC	5	/* DS1287 RTC */
 #define KN02BA_IO_INR_PSU	4	/* power supply unit warning */
 #define KN02BA_IO_INR_RES_3	3	/* unused */
-#define KN02BA_IO_INR_ASC_DATA	2	/* SCSI data ready (discouraged?) */
-#define KN02BA_IO_INR_PBNC	1	/* HALT button debouncer */
-#define KN02BA_IO_INR_PBNO	0	/* ~HALT button debouncer */
+#define KN02BA_IO_INR_ASC_DATA	2	/* SCSI data ready (for PIO) */
+#define KN02BA_IO_INR_PBNC	1	/* ~HALT button debouncer */
+#define KN02BA_IO_INR_PBNO	0	/* HALT button debouncer */
+
+
+/*
+ * Memory Error Register bits.
+ */
+#define KN02BA_MER_RES_27	(1<<27)		/* unused */
+
+/*
+ * Memory Size Register bits.
+ */
+#define KN02BA_MSR_RES_17	(0x3ff<<17)	/* unused */
+
+/*
+ * I/O ASIC System Support Register bits.
+ */
+#define KN02BA_IO_SSR_TXDIS1	(1<<14)		/* SCC1 transmit disable */
+#define KN02BA_IO_SSR_TXDIS0	(1<<13)		/* SCC0 transmit disable */
+#define KN02BA_IO_SSR_RES_12	(1<<12)		/* unused */
+
+#define KN02BA_IO_SSR_LEDS	(0xff<<0)	/* ~diagnostic LEDs */
 
 #endif /* __ASM_MIPS_DEC_KN02BA_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn02ca.h linux-2.4.21-bk34/include/asm-mips/dec/kn02ca.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn02ca.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn02ca.h	2003-08-15 02:54:50.000000000 -0700
@@ -3,7 +3,7 @@
  *
  *	Personal DECstation 5000/xx (Maxine or KN02-CA) definitions.
  *
- *	Copyright (C) 2002  Maciej W. Rozycki
+ *	Copyright (C) 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -16,17 +16,11 @@
 #include <asm/dec/kn02xa.h>		/* For common definitions. */
 
 /*
- * Some port addresses...
- */
-#define KN02CA_IOASIC_BASE	KN02XA_IOASIC_BASE	/* I/O ASIC */
-#define KN02CA_RTC_BASE		KN02XA_RTC_BASE		/* RTC */
-
-/*
  * CPU interrupt bits.
  */
 #define KN02CA_CPU_INR_HALT	6	/* HALT from ACCESS.Bus */
 #define KN02CA_CPU_INR_CASCADE	5	/* I/O ASIC cascade */
-#define KN02CA_CPU_INR_MEMORY	4	/* memory, I/O bus write errors */
+#define KN02CA_CPU_INR_BUS	4	/* memory, I/O bus read/write errors */
 #define KN02CA_CPU_INR_RTC	3	/* DS1287 RTC */
 #define KN02CA_CPU_INR_TIMER	2	/* ARC periodic timer */
 
@@ -35,8 +29,9 @@
  */
 #define KN02CA_IO_INR_FLOPPY	15	/* 82077 FDC */
 #define KN02CA_IO_INR_NVRAM	14	/* (*) NVRAM clear jumper */
-#define KN02CA_IO_INR_POWERON	13	/* (*) power-on reset */
+#define KN02CA_IO_INR_POWERON	13	/* (*) ACCESS.Bus/power-on reset */
 #define KN02CA_IO_INR_TC0	12	/* TURBOchannel slot #0 */
+#define KN02CA_IO_INR_TIMER	12	/* ARC periodic timer (?) */
 #define KN02CA_IO_INR_ISDN	11	/* Am79C30A ISDN */
 #define KN02CA_IO_INR_NRMOD	10	/* (*) NRMOD manufacturing jumper */
 #define KN02CA_IO_INR_ASC	9	/* ASC (NCR53C94) SCSI */
@@ -50,4 +45,35 @@
 #define KN02CA_IO_INR_AB_XMIT	1	/* ACCESS.bus transmit */
 #define KN02CA_IO_INR_AB_RECV	0	/* ACCESS.bus receive */
 
+
+/*
+ * Memory Error Register bits.
+ */
+#define KN02CA_MER_INTR		(1<<27)		/* ARC IRQ status & ack */
+
+/*
+ * Memory Size Register bits.
+ */
+#define KN02CA_MSR_INTREN	(1<<26)		/* ARC periodic IRQ enable */
+#define KN02CA_MSR_MS10EN	(1<<25)		/* 10/1ms IRQ period select */
+#define KN02CA_MSR_PFORCE	(0xf<<21)	/* byte lane error force */
+#define KN02CA_MSR_MABEN	(1<<20)		/* A side VFB address enable */
+#define KN02CA_MSR_LASTBANK	(0x7<<17)	/* onboard RAM bank # */
+
+/*
+ * I/O ASIC System Support Register bits.
+ */
+#define KN03CA_IO_SSR_RES_14	(1<<14)		/* unused */
+#define KN03CA_IO_SSR_RES_13	(1<<13)		/* unused */
+#define KN03CA_IO_SSR_ISDN_RST	(1<<12)		/* ~ISDN (Am79C30A) reset */
+
+#define KN03CA_IO_SSR_FLOPPY_RST (1<<7)		/* ~FDC (82077) reset */
+#define KN03CA_IO_SSR_VIDEO_RST	(1<<6)		/* ~framebuffer reset */
+#define KN03CA_IO_SSR_AB_RST	(1<<5)		/* ACCESS.bus reset */
+#define KN03CA_IO_SSR_RES_4	(1<<4)		/* unused */
+#define KN03CA_IO_SSR_RES_3	(1<<4)		/* unused */
+#define KN03CA_IO_SSR_RES_2	(1<<2)		/* unused */
+#define KN03CA_IO_SSR_RES_1	(1<<1)		/* unused */
+#define KN03CA_IO_SSR_LED	(1<<0)		/* power LED */
+
 #endif /* __ASM_MIPS_DEC_KN02CA_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn02xa.h linux-2.4.21-bk34/include/asm-mips/dec/kn02xa.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn02xa.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn02xa.h	2003-08-15 02:54:50.000000000 -0700
@@ -9,7 +9,7 @@
  *
  * Copyright (C) 1995,1996 by Paul M. Antoine, some code and definitions
  * are by courtesy of Chris Fraser.
- * Copyright (C) 2000, 2002  Maciej W. Rozycki
+ * Copyright (C) 2000, 2002, 2003  Maciej W. Rozycki
  *
  * These are addresses which have to be known early in the boot process.
  * For other addresses refer to tc.h, ioasic_addrs.h and friends.
@@ -18,13 +18,58 @@
 #define __ASM_MIPS_DEC_KN02XA_H
 
 #include <asm/addrspace.h>
+#include <asm/dec/ioasic_addrs.h>
+
+#define KN02XA_SLOT_BASE	KSEG1ADDR(0x1c000000)
 
 /*
  * Some port addresses...
  */
-#define KN02XA_IOASIC_BASE	KSEG1ADDR(0x1c040000)	/* I/O ASIC */
-#define KN02XA_RTC_BASE		KSEG1ADDR(0x1c200000)	/* RTC */
+#define KN02XA_IOASIC_BASE    (KN02XA_SLOT_BASE + IOASIC_IOCTL)	/* I/O ASIC */
+#define KN02XA_RTC_BASE		(KN02XA_SLOT_BASE + IOASIC_TOY)	/* RTC */
+
+
+/*
+ * Memory control ASIC registers.
+ */
+#define KN02XA_MER	KSEG1ADDR(0x0c400000)	/* memory error register */
+#define KN02XA_MSR	KSEG1ADDR(0x0c800000)	/* memory size register */
+
+/*
+ * CPU control ASIC registers.
+ */
+#define KN02XA_MEM_CONF	KSEG1ADDR(0x0e000000)	/* write timeout config */
+#define KN02XA_EAR	KSEG1ADDR(0x0e000004)	/* error address register */
+#define KN02XA_BOOT0	KSEG1ADDR(0x0e000008)	/* boot 0 register */
+#define KN02XA_MEM_INTR	KSEG1ADDR(0x0e00000c)	/* write err IRQ stat & ack */
 
-#define KN02XA_IOASIC_REG(r)	(KN02XA_IOASIC_BASE+(r))
+/*
+ * Memory Error Register bits, common definitions.
+ * The rest is defined in system-specific headers.
+ */
+#define KN02XA_MER_RES_28	(0xf<<28)	/* unused */
+#define KN02XA_MER_RES_17	(0x3ff<<17)	/* unused */
+#define KN02XA_MER_PAGERR	(1<<16)		/* 2k page boundary error */
+#define KN02XA_MER_TRANSERR	(1<<15)		/* transfer length error */
+#define KN02XA_MER_PARDIS	(1<<14)		/* parity error disable */
+#define KN02XA_MER_RES_12	(0x3<<12)	/* unused */
+#define KN02XA_MER_BYTERR	(0xf<<8)	/* byte lane error bitmask */
+#define KN02XA_MER_RES_0	(0xff<<0)	/* unused */
+
+/*
+ * Memory Size Register bits, common definitions.
+ * The rest is defined in system-specific headers.
+ */
+#define KN02XA_MSR_RES_27	(0x1f<<27)	/* unused */
+#define KN02XA_MSR_RES_14	(0x7<<14)	/* unused */
+#define KN02XA_MSR_SIZE		(1<<13)		/* 16M/4M stride */
+#define KN02XA_MSR_RES_0	(0x1fff<<0)	/* unused */
+
+/*
+ * Error Address Register bits.
+ */
+#define KN02XA_EAR_RES_29	(0x7<<29)	/* unused */
+#define KN02XA_EAR_ADDRESS	(0x7ffffff<<2)	/* address involved */
+#define KN02XA_EAR_RES_0	(0x3<<0)	/* unused */
 
 #endif /* __ASM_MIPS_DEC_KN02XA_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn03.h linux-2.4.21-bk34/include/asm-mips/dec/kn03.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn03.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn03.h	2003-08-15 02:54:50.000000000 -0700
@@ -10,34 +10,30 @@
  *
  * Copyright (C) 1995,1996 by Paul M. Antoine, some code and definitions
  * are by courtesy of Chris Fraser.
- * Copyright (C) 2000, 2002  Maciej W. Rozycki
- *
- * These are addresses which have to be known early in the boot process.
- * For other addresses refer to tc.h ioasic_addrs.h and friends.
+ * Copyright (C) 2000, 2002, 2003  Maciej W. Rozycki
  */
 #ifndef __ASM_MIPS_DEC_KN03_H
 #define __ASM_MIPS_DEC_KN03_H
 
 #include <asm/addrspace.h>
+#include <asm/dec/ecc.h>
+#include <asm/dec/ioasic_addrs.h>
+
+#define KN03_SLOT_BASE	KSEG1ADDR(0x1f800000)
 
 /*
  * Some port addresses...
  */
-#define KN03_IOASIC_BASE	KSEG1ADDR(0x1f840000)	/* I/O ASIC */
-#define KN03_RTC_BASE		KSEG1ADDR(0x1fa00000)	/* RTC */
-#define KN03_MCR_BASE		KSEG1ADDR(0x1fac0000)	/* MCR */
-
-#define KN03_MCR_BNK32M		(1<<10)			/* 32M stride */
-#define KN03_MCR_ECCEN		(1<<13)			/* ECC enabled */
-
-#define KN03_IOASIC_REG(r)	(KN03_IOASIC_BASE+(r))
+#define KN03_IOASIC_BASE	(KN03_SLOT_BASE + IOASIC_IOCTL)	/* I/O ASIC */
+#define KN03_RTC_BASE		(KN03_SLOT_BASE + IOASIC_TOY)	/* RTC */
+#define KN03_MCR_BASE		(KN03_SLOT_BASE + IOASIC_MCR)	/* MCR */
 
 
 /*
  * CPU interrupt bits.
  */
 #define KN03_CPU_INR_HALT	6	/* HALT button */
-#define KN03_CPU_INR_MEMORY	5	/* memory, I/O bus write errors */
+#define KN03_CPU_INR_BUS	5	/* memory, I/O bus read/write errors */
 #define KN03_CPU_INR_RES_4	4	/* unused */
 #define KN03_CPU_INR_RTC	3	/* DS1287 RTC */
 #define KN03_CPU_INR_CASCADE	2	/* I/O ASIC cascade */
@@ -55,11 +51,33 @@
 #define KN03_IO_INR_LANCE	8	/* LANCE (Am7990) Ethernet */
 #define KN03_IO_INR_SCC1	7	/* SCC (Z85C30) serial #1 */
 #define KN03_IO_INR_SCC0	6	/* SCC (Z85C30) serial #0 */
-#define KN03_IO_INR_RTC		5	/* DS1287 RTC (?) */
+#define KN03_IO_INR_RTC		5	/* DS1287 RTC */
 #define KN03_IO_INR_PSU		4	/* power supply unit warning */
 #define KN03_IO_INR_RES_3	3	/* unused */
-#define KN03_IO_INR_ASC_DATA	2	/* SCSI data ready (discouraged?) (?) */
-#define KN03_IO_INR_PBNC	1	/* HALT button debouncer */
-#define KN03_IO_INR_PBNO	0	/* ~HALT button debouncer */
+#define KN03_IO_INR_ASC_DATA	2	/* SCSI data ready (for PIO) */
+#define KN03_IO_INR_PBNC	1	/* ~HALT button debouncer */
+#define KN03_IO_INR_PBNO	0	/* HALT button debouncer */
+
+
+/*
+ * Memory Control Register bits.
+ */
+#define KN03_MCR_RES_16		(0xffff<<16)	/* unused */
+#define KN03_MCR_DIAGCHK	(1<<15)		/* diagn/norml ECC reads */
+#define KN03_MCR_DIAGGEN	(1<<14)		/* diagn/norml ECC writes */
+#define KN03_MCR_CORRECT	(1<<13)		/* ECC correct/check */
+#define KN03_MCR_RES_11		(0x3<<12)	/* unused */
+#define KN03_MCR_BNK32M		(1<<10)		/* 32M/8M stride */
+#define KN03_MCR_RES_7		(0x7<<7)	/* unused */
+#define KN03_MCR_CHECK		(0x7f<<0)	/* diagnostic check bits */
+
+/*
+ * I/O ASIC System Support Register bits.
+ */
+#define KN03_IO_SSR_TXDIS1	(1<<14)		/* SCC1 transmit disable */
+#define KN03_IO_SSR_TXDIS0	(1<<13)		/* SCC0 transmit disable */
+#define KN03_IO_SSR_RES_12	(1<<12)		/* unused */
+
+#define KN03_IO_SSR_LEDS	(0xff<<0)	/* ~diagnostic LEDs */
 
 #endif /* __ASM_MIPS_DEC_KN03_H */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn05.h linux-2.4.21-bk34/include/asm-mips/dec/kn05.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn05.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn05.h	2003-08-15 02:54:50.000000000 -0700
@@ -1,10 +1,10 @@
 /*
  *	include/asm-mips/dec/kn05.h
  *
- *	DECstation 5000/260 (4max+ or KN05) and DECsystem 5900-260
+ *	DECstation 5000/260 (4max+ or KN05) and DECsystem 5900/260
  *	definitions.
  *
- *	Copyright (C) 2002  Maciej W. Rozycki
+ *	Copyright (C) 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -31,21 +31,21 @@
 #define KN05_IOCTL	(17*IOASIC_SLOT_SIZE)	/* I/O ASIC */
 #define KN05_ESAR	(18*IOASIC_SLOT_SIZE)	/* LANCE MAC address chip */
 #define KN05_LANCE	(19*IOASIC_SLOT_SIZE)	/* LANCE Ethernet */
-#define KN05_MB_INT	(20*IOASIC_SLOT_SIZE)	/* MB interrupt register? */
-#define KN05_MB_UNKN_0	(21*IOASIC_SLOT_SIZE)	/* MB unknown register */
-#define KN05_MB_UNKN_1	(22*IOASIC_SLOT_SIZE)	/* MB unknown register */
+#define KN05_MB_INT	(20*IOASIC_SLOT_SIZE)	/* MB interrupt register */
+#define KN05_MB_EA	(21*IOASIC_SLOT_SIZE)	/* MB error address? */
+#define KN05_MB_EC	(22*IOASIC_SLOT_SIZE)	/* MB error ??? */
 #define KN05_MB_CSR	(23*IOASIC_SLOT_SIZE)	/* MB control & status */
-#define KN05_RESERVED_0	(24*IOASIC_SLOT_SIZE)	/* unused? */
-#define KN05_RESERVED_1	(25*IOASIC_SLOT_SIZE)	/* unused? */
-#define KN05_RESERVED_2	(26*IOASIC_SLOT_SIZE)	/* unused? */
-#define KN05_RESERVED_3	(27*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_24	(24*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_25	(25*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_26	(26*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_27	(27*IOASIC_SLOT_SIZE)	/* unused? */
 #define KN05_SCSI	(28*IOASIC_SLOT_SIZE)	/* ASC SCSI */
-#define KN05_RESERVED_4	(29*IOASIC_SLOT_SIZE)	/* unused? */
-#define KN05_RESERVED_5	(30*IOASIC_SLOT_SIZE)	/* unused? */
-#define KN05_RESERVED_6	(31*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_29	(29*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_30	(30*IOASIC_SLOT_SIZE)	/* unused? */
+#define KN05_RES_31	(31*IOASIC_SLOT_SIZE)	/* unused? */
 
 /*
- * Bits for the MB interrupt (?) register.
+ * Bits for the MB interrupt register.
  * The register appears read-only.
  */
 #define KN05_MB_INT_TC		(1<<0)		/* TURBOchannel? */
@@ -55,7 +55,7 @@
  * Bits for the MB control & status register.
  * Set to 0x00bf8001 on my system by the ROM.
  */
-#define KN05_MB_CSR_PF		(1<<0)		/* ??? */
+#define KN05_MB_CSR_PF		(1<<0)		/* PreFetching enable? */
 #define KN05_MB_CSR_F		(1<<1)		/* ??? */
 #define KN05_MB_CSR_ECC		(0xff<<2)	/* ??? */
 #define KN05_MB_CSR_OD		(1<<10)		/* ??? */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/kn230.h linux-2.4.21-bk34/include/asm-mips/dec/kn230.h
--- linux-2.4.21-bk33/include/asm-mips/dec/kn230.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/kn230.h	2003-08-15 02:54:50.000000000 -0700
@@ -1,9 +1,9 @@
 /*
  *	include/asm-mips/dec/kn230.h
  *
- *	DECstation 5100 (MIPSmate or KN230) definitions.
+ *	DECsystem 5100 (MIPSmate or KN230) definitions.
  *
- *	Copyright (C) 2002  Maciej W. Rozycki
+ *	Copyright (C) 2002, 2003  Maciej W. Rozycki
  *
  *	This program is free software; you can redistribute it and/or
  *	modify it under the terms of the GNU General Public License
@@ -17,7 +17,7 @@
  * CPU interrupt bits.
  */
 #define KN230_CPU_INR_HALT	6	/* HALT button */
-#define KN230_CPU_INR_MEMORY	5	/* memory, I/O bus write errors */
+#define KN230_CPU_INR_BUS	5	/* memory, I/O bus read/write errors */
 #define KN230_CPU_INR_RTC	4	/* DS1287 RTC */
 #define KN230_CPU_INR_SII	3	/* SII (DC7061) SCSI */
 #define KN230_CPU_INR_LANCE	3	/* LANCE (Am7990) Ethernet */
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/machtype.h linux-2.4.21-bk34/include/asm-mips/dec/machtype.h
--- linux-2.4.21-bk33/include/asm-mips/dec/machtype.h	2002-11-28 15:53:15.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/machtype.h	2003-08-15 02:54:50.000000000 -0700
@@ -16,10 +16,12 @@
 #define TURBOCHANNEL	(mips_machtype == MACH_DS5000_200 || \
 			 mips_machtype == MACH_DS5000_1XX || \
 			 mips_machtype == MACH_DS5000_XX  || \
-			 mips_machtype == MACH_DS5000_2X0)
+			 mips_machtype == MACH_DS5000_2X0 || \
+			 mips_machtype == MACH_DS5900)
 
 #define IOASIC		(mips_machtype == MACH_DS5000_1XX || \
 			 mips_machtype == MACH_DS5000_XX  || \
-			 mips_machtype == MACH_DS5000_2X0)
+			 mips_machtype == MACH_DS5000_2X0 || \
+			 mips_machtype == MACH_DS5900)
 
 #endif
diff -urN linux-2.4.21-bk33/include/asm-mips/dec/prom.h linux-2.4.21-bk34/include/asm-mips/dec/prom.h
--- linux-2.4.21-bk33/include/asm-mips/dec/prom.h	1969-12-31 16:00:00.000000000 -0800
+++ linux-2.4.21-bk34/include/asm-mips/dec/prom.h	2003-08-15 02:54:50.000000000 -0700
@@ -0,0 +1,167 @@
+/*
+ *	DECstation PROM interface.
+ *
+ *	Copyright (C) 2002  Maciej W. Rozycki
+ *
+ *	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.
+ *
+ *	Based on arch/mips/dec/prom/prom.h by the Anonymous.
+ */
+#ifndef __ASM_DEC_PROM_H
+#define __ASM_DEC_PROM_H
+
+#include <linux/types.h>
+
+#include <asm/addrspace.h>
+
+/*
+ * PMAX/3MAX PROM entry points for DS2100/3100's and DS5000/2xx's.
+ * Many of these will work for MIPSen as well!
+ */
+#define VEC_RESET		(u64 *)KSEG1ADDR(0x1fc00000)
+							/* Prom base address */
+
+#define PMAX_PROM_ENTRY(x)	(VEC_RESET + (x))	/* Prom jump table */
+
+#define PMAX_PROM_HALT		PMAX_PROM_ENTRY(2)	/* valid on MIPSen */
+#define PMAX_PROM_AUTOBOOT	PMAX_PROM_ENTRY(5)	/* valid on MIPSen */
+#define PMAX_PROM_OPEN		PMAX_PROM_ENTRY(6)
+#define PMAX_PROM_READ		PMAX_PROM_ENTRY(7)
+#define PMAX_PROM_CLOSE		PMAX_PROM_ENTRY(10)
+#define PMAX_PROM_LSEEK		PMAX_PROM_ENTRY(11)
+#define PMAX_PROM_GETCHAR	PMAX_PROM_ENTRY(12)
+#define PMAX_PROM_PUTCHAR	PMAX_PROM_ENTRY(13)	/* 12 on MIPSen */
+#define PMAX_PROM_GETS		PMAX_PROM_ENTRY(15)
+#define PMAX_PROM_PRINTF	PMAX_PROM_ENTRY(17)
+#define PMAX_PROM_GETENV	PMAX_PROM_ENTRY(33)	/* valid on MIPSen */
+
+
+/*
+ * Magic number indicating REX PROM available on DECstation.  Found in
+ * register a2 on transfer of control to program from PROM.
+ */
+#define REX_PROM_MAGIC		0x30464354
+
+#ifdef CONFIG_MIPS64
+
+#define prom_is_rex(magic)	1	/* KN04 and KN05 are REX PROMs.  */
+
+#else /* !CONFIG_MIPS64 */
+
+#define prom_is_rex(magic)	((magic) == REX_PROM_MAGIC)
+
+#endif /* !CONFIG_MIPS64 */
+
+
+/*
+ * 3MIN/MAXINE PROM entry points for DS5000/1xx's, DS5000/xx's and
+ * DS5000/2x0.
+ */
+#define REX_PROM_GETBITMAP	0x84/4	/* get mem bitmap */
+#define REX_PROM_GETCHAR	0x24/4	/* getch() */
+#define REX_PROM_GETENV		0x64/4	/* get env. variable */
+#define REX_PROM_GETSYSID	0x80/4	/* get system id */
+#define REX_PROM_GETTCINFO	0xa4/4
+#define REX_PROM_PRINTF		0x30/4	/* printf() */
+#define REX_PROM_SLOTADDR	0x6c/4	/* slotaddr */
+#define REX_PROM_BOOTINIT	0x54/4	/* open() */
+#define REX_PROM_BOOTREAD	0x58/4	/* read() */
+#define REX_PROM_CLEARCACHE	0x7c/4
+
+
+/*
+ * Used by rex_getbitmap().
+ */
+typedef struct {
+	int pagesize;
+	unsigned char bitmap[0];
+} memmap;
+
+
+/*
+ * Function pointers as read from a PROM's callback vector.
+ */
+extern int (*__rex_bootinit)(void);
+extern int (*__rex_bootread)(void);
+extern int (*__rex_getbitmap)(memmap *);
+extern unsigned long *(*__rex_slot_address)(int);
+extern void *(*__rex_gettcinfo)(void);
+extern int (*__rex_getsysid)(void);
+extern void (*__rex_clear_cache)(void);
+
+extern int (*__prom_getchar)(void);
+extern char *(*__prom_getenv)(char *);
+extern int (*__prom_printf)(char *, ...);
+
+extern int (*__pmax_open)(char*, int);
+extern int (*__pmax_lseek)(int, long, int);
+extern int (*__pmax_read)(int, void *, int);
+extern int (*__pmax_close)(int);
+
+
+#ifdef CONFIG_MIPS64
+
+/*
+ * On MIPS64 we have to call PROM functions via a helper
+ * dispatcher to accomodate ABI incompatibilities.
+ */
+#define __DEC_PROM_O32 __attribute__((alias("call_o32")))
+
+int _rex_bootinit(int (*)(void)) __DEC_PROM_O32;
+int _rex_bootread(int (*)(void)) __DEC_PROM_O32;
+int _rex_getbitmap(int (*)(memmap *), memmap *) __DEC_PROM_O32;
+unsigned long *_rex_slot_address(unsigned long *(*)(int), int) __DEC_PROM_O32;
+void *_rex_gettcinfo(void *(*)(void)) __DEC_PROM_O32;
+int _rex_getsysid(int (*)(void)) __DEC_PROM_O32;
+void _rex_clear_cache(void (*)(void)) __DEC_PROM_O32;
+
+int _prom_getchar(int (*)(void)) __DEC_PROM_O32;
+char *_prom_getenv(char *(*)(char *), char *) __DEC_PROM_O32;
+int _prom_printf(int (*)(char *, ...), char *, ...) __DEC_PROM_O32;
+
+
+#define rex_bootinit()		_rex_bootinit(__rex_bootinit)
+#define rex_bootread()		_rex_bootread(__rex_bootread)
+#define rex_getbitmap(x)	_rex_getbitmap(__rex_getbitmap, x)
+#define rex_slot_address(x)	_rex_slot_address(__rex_slot_address, x)
+#define rex_gettcinfo()		_rex_gettcinfo(__rex_gettcinfo)
+#define rex_getsysid()		_rex_getsysid(__rex_getsysid)
+#define rex_clear_cache()	_rex_clear_cache(__rex_clear_cache)
+
+#define prom_getchar()		_prom_getchar(__prom_getchar)
+#define prom_getenv(x)		_prom_getenv(__prom_getenv, x)
+#define prom_printf(x...)	_prom_printf(__prom_printf, x)
+
+#else /* !CONFIG_MIPS64 */
+
+/*
+ * On plain MIPS we just call PROM functions directly.
+ */
+#define rex_bootinit		__rex_bootinit
+#define rex_bootread		__rex_bootread
+#define rex_getbitmap		__rex_getbitmap
+#define rex_slot_address	__rex_slot_address
+#define rex_gettcinfo		__rex_gettcinfo
+#define rex_getsysid		__rex_getsysid
+#define rex_clear_cache		__rex_clear_cache
+
+#define prom_getchar		__prom_getchar
+#define prom_getenv		__prom_getenv
+#define prom_printf		__prom_printf
+
+#define pmax_open		__pmax_open
+#define pmax_lseek		__pmax_lseek
+#define pmax_read		__pmax_read
+#define pmax_close		__pmax_close
+
+#endif /* !CONFIG_MIPS64 */
+
+
+extern void prom_meminit(u32);
+extern void prom_identify_arch(u32);
+extern void prom_init_cmdline(s32, s32 *, u32);
+
+#endif /* __ASM_DEC_PROM_H */
