Summary:
  SMP related modules.
   - add PC-9800 bus spec.
diffstat:
  arch/i386/kernel/apic.c    |   16 +++++++++++++---
  arch/i386/kernel/io_apic.c |   25 +++++++++++++++++++++++--
  arch/i386/kernel/mpparse.c |   35 ++++++++++++++++++++++++++++++++++-
  arch/i386/kernel/smpboot.c |   14 ++++++++++++++
  include/asm-i386/mpspec.h  |    4 +++-
  include/asm-i386/smpboot.h |    9 +++++++++
  6 files changed, 96 insertions(+), 7 deletions(-)
patch:
diff -urN linux/arch/i386/kernel/apic.c linux98/arch/i386/kernel/apic.c
--- linux/arch/i386/kernel/apic.c	Wed Oct 16 13:20:29 2002
+++ linux98/arch/i386/kernel/apic.c	Wed Oct 16 15:40:20 2002
@@ -33,6 +33,8 @@
  #include <asm/arch_hooks.h>
  #include "mach_apic.h"
  +#include "io_ports.h"
+
  void __init apic_intr_init(void)
  {
  #ifdef CONFIG_SMP
@@ -135,9 +137,13 @@
  		 * PIC mode, enable APIC mode in the IMCR, i.e.
  		 * connect BSP's local APIC to INT and NMI lines.
  		 */
+#ifndef CONFIG_PC9800
  		printk("leaving PIC mode, enabling APIC mode.\n");
  		outb(0x70, 0x22);
  		outb(0x01, 0x23);
+#else
+		printk("On NEC98, Changing mode from PIC to APIC isNOT supported yet.\n");
+#endif
  	}
  }
  @@ -150,9 +156,13 @@
  		 * interrupts, including IPIs, won't work beyond
  		 * this point!  The only exception are INIT IPIs.
  		 */
+#ifndef CONFIG_PC9800
  		printk("disabling APIC mode, entering PIC mode.\n");
  		outb(0x70, 0x22);
  		outb(0x00, 0x23);
+#else
+		printk("On NEC98, Changing mode from APIC to PIC isNOT supported yet.\n");
+#endif
  	}
  }
  @@ -759,9 +769,9 @@
   	spin_lock_irqsave(&i8253_lock, flags);
  -	outb_p(0x00, 0x43);
-	count = inb_p(0x40);
-	count |= inb_p(0x40) << 8;
+	outb_p(0x00, PIT_MODE);
+	count = inb_p(PIT_CH0);
+	count |= inb_p(PIT_CH0) << 8;
   	spin_unlock_irqrestore(&i8253_lock, flags);
  diff -urN linux/arch/i386/kernel/io_apic.c linux98/arch/i386/kernel/io_apic.c
--- linux/arch/i386/kernel/io_apic.c	Sat Oct 19 13:01:22 2002
+++ linux98/arch/i386/kernel/io_apic.c	Sat Oct 19 16:22:51 2002
@@ -37,6 +37,8 @@
  #include <asm/desc.h>
  #include "mach_apic.h"
  +#include "io_ports.h"
+
  #undef APIC_LOCKUP_DEBUG
   #define APIC_LOCKUP_DEBUG
@@ -354,7 +356,9 @@
   		if ((mp_bus_id_to_type[lbus] == MP_BUS_ISA ||
  		     mp_bus_id_to_type[lbus] == MP_BUS_EISA ||
-		     mp_bus_id_to_type[lbus] == MP_BUS_MCA) &&
+		     mp_bus_id_to_type[lbus] == MP_BUS_MCA ||
+		     mp_bus_id_to_type[lbus] == MP_BUS_NEC98
+		    ) &&
  		    (mp_irqs[i].mpc_irqtype == type) &&
  		    (mp_irqs[i].mpc_srcbusirq == irq))
  @@ -448,6 +452,12 @@
  #define default_MCA_trigger(idx)	(1)
  #define default_MCA_polarity(idx)	(0)
  +/* NEC98 interrupts are always polarity zero edge triggered,
+ * when listed as conforming in the MP table. */
+
+#define default_NEC98_trigger(idx)     (0)
+#define default_NEC98_polarity(idx)    (0)
+
  static int __init MPBIOS_polarity(int idx)
  {
  	int bus = mp_irqs[idx].mpc_srcbus;
@@ -482,6 +492,11 @@
  					polarity = default_MCA_polarity(idx);
  					break;
  				}
+				case MP_BUS_NEC98: /* NEC 98 pin */
+				{
+					polarity = default_NEC98_polarity(idx);
+					break;
+				}
  				default:
  				{
  					printk(KERN_WARNING "broken BIOS!!\n");
@@ -551,6 +566,11 @@
  					trigger = default_MCA_trigger(idx);
  					break;
  				}
+				case MP_BUS_NEC98: /* NEC 98 pin */
+				{
+					trigger = default_NEC98_trigger(idx);
+					break;
+				}
  				default:
  				{
  					printk(KERN_WARNING "broken BIOS!!\n");
@@ -612,6 +632,7 @@
  		case MP_BUS_ISA: /* ISA pin */
  		case MP_BUS_EISA:
  		case MP_BUS_MCA:
+		case MP_BUS_NEC98:
  		{
  			irq = mp_irqs[idx].mpc_srcbusirq;
  			break;
@@ -1718,7 +1739,7 @@
   * Additionally, something is definitely wrong with irq9
   * on PIIX4 boards.
   */
-#define PIC_IRQS	(1<<2)
+#define PIC_IRQS	(1 << PIC_CASCADE_IR)
   void __init setup_IO_APIC(void)
  {
diff -urN linux/arch/i386/kernel/mpparse.c linux98/arch/i386/kernel/mpparse.c
--- linux/arch/i386/kernel/mpparse.c	Wed Oct 16 13:20:29 2002
+++ linux98/arch/i386/kernel/mpparse.c	Wed Oct 16 15:40:20 2002
@@ -236,6 +236,8 @@
  		mp_current_pci_id++;
  	} else if (strncmp(str, BUSTYPE_MCA, sizeof(BUSTYPE_MCA)-1) == 0) {
  		mp_bus_id_to_type[m->mpc_busid] = MP_BUS_MCA;
+	} else if (strncmp(str, BUSTYPE_NEC98, sizeof(BUSTYPE_NEC98)-1) == 0) {
+		mp_bus_id_to_type[m->mpc_busid] = MP_BUS_NEC98;
  	} else {
  		printk("Unknown bustype %s - ignoring\n", str);
  	}
@@ -681,7 +683,12 @@
  		 * Read the physical hardware table.  Anything here will
  		 * override the defaults.
  		 */
-		if (!smp_read_mpc((void *)mpf->mpf_physptr)) {
+#ifndef CONFIG_PC9800
+		if (!smp_read_mpc((void *)mpf->mpf_physptr))
+#else
+		if (!smp_read_mpc(phys_to_virt(mpf->mpf_physptr)))
+#endif
+		{
  			smp_found_config = 0;
  			printk(KERN_ERR "BIOS bug, MP table errors detected!...\n");
  			printk(KERN_ERR "... disabling SMP support. (tell your hw vendor)\n");
@@ -735,8 +742,30 @@
  			printk("found SMP MP-table at %08lx\n",
  						virt_to_phys(mpf));
  			reserve_bootmem(virt_to_phys(mpf), PAGE_SIZE);
+#ifndef CONFIG_PC9800
  			if (mpf->mpf_physptr)
  				reserve_bootmem(mpf->mpf_physptr, PAGE_SIZE);
+#else
+			/*
+			 * PC-9800's MPC table places on the very last of
+			 * physical memory; so that simply reserving PAGE_SIZE
+			 * from mpg->mpf_physptr yields BUG() in
+			 * reserve_bootmem.
+			 */
+			if (mpf->mpf_physptr) {
+				/*
+				 * We cannot access to MPC table to compute
+				 * table size yet, as only few megabytes from
+				 * the bottom is mapped now.
+				 */
+				unsigned long size = PAGE_SIZE;
+				unsigned long end = max_low_pfn * PAGE_SIZE;
+				if (mpf->mpf_physptr + size > end)
+					size = end - mpf->mpf_physptr;
+				reserve_bootmem(mpf->mpf_physptr, size);
+			}
+#endif
+
  			mpf_found = mpf;
  			return 1;
  		}
@@ -748,7 +777,9 @@
   void __init find_smp_config (void)
  {
+#ifndef CONFIG_PC9800
  	unsigned int address;
+#endif
   	/*
  	 * FIXME: Linux assumes you have 640K of base ram..
@@ -762,6 +793,7 @@
  		smp_scan_config(639*0x400,0x400) ||
  			smp_scan_config(0xF0000,0x10000))
  		return;
+#ifndef CONFIG_PC9800	/* PC-9800 has no EBDA area? */
  	/*
  	 * If it is an SMP machine we should know now, unless the
  	 * configuration is in an EISA/MCA bus machine with an
@@ -784,6 +816,7 @@
  	smp_scan_config(address, 0x400);
  	if (smp_found_config)
  		printk(KERN_WARNING "WARNING: MP table in the EBDA can be UNSAFE, contact linux-smp@vger.kernel.org if you experience SMP problems!\n");
+#endif
  }
   diff -urN linux/arch/i386/kernel/smpboot.c linux98/arch/i386/kernel/smpboot.c
--- linux/arch/i386/kernel/smpboot.c	Wed Oct 16 13:20:29 2002
+++ linux98/arch/i386/kernel/smpboot.c	Wed Oct 16 15:40:20 2002
@@ -821,13 +821,27 @@
  		nmi_low = *((volatile unsigned short *) TRAMPOLINE_LOW);
  	}  +#ifndef CONFIG_PC9800
  	CMOS_WRITE(0xa, 0xf);
+#else
+	/* reset code is stored in 8255 on PC-9800. */
+	outb(0x0e, 0x37);	/* SHUT0 = 0 */
+#endif
  	local_flush_tlb();
  	Dprintk("1.\n");
  	*((volatile unsigned short *) TRAMPOLINE_HIGH) = start_eip >> 4;
  	Dprintk("2.\n");
  	*((volatile unsigned short *) TRAMPOLINE_LOW) = start_eip & 0xf;
  	Dprintk("3.\n");
+#ifdef CONFIG_PC9800
+	/*
+	 * On PC-9800, continuation on warm reset is done by loading
+	 * %ss:%sp from 0x0000:0404 and executing 'lret', so:
+	 */
+	/* 0x3f0 is on unused interrupt vector and should be safe... */
+	*((volatile unsigned long *) phys_to_virt(0x404)) = 0x000003f0;
+	Dprintk("4.\n");
+#endif
   	/*
  	 * Be paranoid about clearing APIC errors.
diff -urN linux/include/asm-i386/mpspec.h linux98/include/asm-i386/mpspec.h
--- linux/include/asm-i386/mpspec.h	Fri Apr 12 13:58:13 2002
+++ linux98/include/asm-i386/mpspec.h	Fri Apr 12 14:02:42 2002
@@ -105,6 +105,7 @@
  #define BUSTYPE_TC	"TC"
  #define BUSTYPE_VME	"VME"
  #define BUSTYPE_XPRESS	"XPRESS"
+#define BUSTYPE_NEC98	"NEC98"
   struct mpc_config_ioapic
  {
@@ -195,7 +196,8 @@
  	MP_BUS_ISA = 1,
  	MP_BUS_EISA,
  	MP_BUS_PCI,
-	MP_BUS_MCA
+	MP_BUS_MCA,
+	MP_BUS_NEC98
  };
  extern int mp_bus_id_to_type [MAX_MP_BUSSES];
  extern int mp_bus_id_to_node [MAX_MP_BUSSES];
diff -urN linux/include/asm-i386/smpboot.h linux98/include/asm-i386/smpboot.h
--- linux/include/asm-i386/smpboot.h	Sat Oct 12 13:22:19 2002
+++ linux98/include/asm-i386/smpboot.h	Sat Oct 12 19:33:46 2002
@@ -13,8 +13,17 @@
   #define TRAMPOLINE_LOW phys_to_virt(0x8)
   #define TRAMPOLINE_HIGH phys_to_virt(0xa)
  #else /* !CONFIG_CLUSTERED_APIC */
+ #ifndef CONFIG_PC9800
   #define TRAMPOLINE_LOW phys_to_virt(0x467)
   #define TRAMPOLINE_HIGH phys_to_virt(0x469)
+ #else  /* CONFIG_PC9800 */
+  /*
+   * On PC-9800, continuation on warm reset is done by loading
+   * %ss:%sp from 0x0000:0404 and executing 'lret', so:
+   */
+  #define TRAMPOLINE_LOW phys_to_virt(0x4fa)
+  #define TRAMPOLINE_HIGH phys_to_virt(0x4fc)
+ #endif /* !CONFIG_PC9800 */
  #endif /* CONFIG_CLUSTERED_APIC */
   #ifdef CONFIG_CLUSTERED_APIC
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/