From: Ravikiran G Thirumalai Introduce vSMP arch to the kernel. This patch: 1. Adds CONFIG_X86_VSMP 2. Adds machine specific macros for local_irq_disabled, local_irq_enabled and irqs_disabled 3. Writes to the vSMP CTL device to indicate kernel compiled with CONFIG_VSMP Signed-off-by: Ravikiran Thirumalai Signed-off-by: Shai Fultheim Cc: Andi Kleen Signed-off-by: Andrew Morton --- arch/x86_64/Kconfig | 18 +++++++++++++++++ arch/x86_64/kernel/Makefile | 1 arch/x86_64/kernel/vsmp.c | 45 ++++++++++++++++++++++++++++++++++++++++++++ include/asm-x86_64/system.h | 21 ++++++++++++++++++-- include/linux/pci_ids.h | 3 ++ 5 files changed, 86 insertions(+), 2 deletions(-) diff -puN arch/x86_64/Kconfig~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch arch/x86_64/Kconfig --- devel/arch/x86_64/Kconfig~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch 2005-12-22 05:08:46.000000000 -0800 +++ devel-akpm/arch/x86_64/Kconfig 2005-12-22 05:08:46.000000000 -0800 @@ -79,6 +79,24 @@ source "init/Kconfig" menu "Processor type and features" choice + prompt "Subarchitecture Type" + default X86_PC + +config X86_PC + bool "PC-compatible" + help + Choose this option if your computer is a standard PC or compatible. + +config X86_VSMP + bool "Support for ScaleMP vSMP" + help + Support for ScaleMP vSMP systems. Say 'Y' here if this kernel is + supposed to run on these EM64T-based machines. Only choose this option + if you have one of these machines. + +endchoice + +choice prompt "Processor family" default MK8 diff -puN arch/x86_64/kernel/Makefile~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch arch/x86_64/kernel/Makefile --- devel/arch/x86_64/kernel/Makefile~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch 2005-12-22 05:08:46.000000000 -0800 +++ devel-akpm/arch/x86_64/kernel/Makefile 2005-12-22 05:08:46.000000000 -0800 @@ -31,6 +31,7 @@ obj-$(CONFIG_GART_IOMMU) += pci-gart.o a obj-$(CONFIG_DUMMY_IOMMU) += pci-nommu.o pci-dma.o obj-$(CONFIG_KPROBES) += kprobes.o obj-$(CONFIG_X86_PM_TIMER) += pmtimer.o +obj-$(CONFIG_X86_VSMP) += vsmp.o obj-$(CONFIG_MODULES) += module.o diff -puN arch/x86_64/kernel/vsmp.c~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch arch/x86_64/kernel/vsmp.c --- devel/arch/x86_64/kernel/vsmp.c~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch 2005-12-22 05:08:46.000000000 -0800 +++ devel-akpm/arch/x86_64/kernel/vsmp.c 2005-12-22 05:08:46.000000000 -0800 @@ -0,0 +1,45 @@ +/* + * vSMPowered(tm) systems specific initialization + * Copyright (C) 2005 ScaleMP Inc. + * + * Use of this code is subject to the terms and conditions of the + * GNU general public license version 2. See "COPYING" or + * http://www.gnu.org/licenses/gpl.html + * + * Ravikiran Thirumalai , + * Shai Fultheim + */ + +#include +#include +#include +#include + +static int __init vsmp_init(void) +{ + void *address; + unsigned int cap, ctl; + + /* Check if we are running on a ScaleMP vSMP box */ + if ((read_pci_config_16(0, 0x1f, 0, PCI_VENDOR_ID) != PCI_VENDOR_ID_SCALEMP) || + (read_pci_config_16(0, 0x1f, 0, PCI_DEVICE_ID) != PCI_DEVICE_ID_SCALEMP_VSMP_CTL)) + return 0; + + /* set vSMP magic bits to indicate vSMP capable kernel */ + address = ioremap(read_pci_config(0, 0x1f, 0, PCI_BASE_ADDRESS_0), 8); + cap = readl(address); + ctl = readl(address + 4); + printk("vSMP CTL: capabilities:0x%08x control:0x%08x\n", cap, ctl); + if (cap & ctl & (1 << 4)) { + /* Turn on vSMP IRQ fastpath handling (see system.h) */ + ctl &= ~(1 << 4); + writel(ctl, address + 4); + ctl = readl(address + 4); + printk("vSMP CTL: control set to:0x%08x\n", ctl); + } + + iounmap(address); + return 0; +} + +core_initcall(vsmp_init); diff -puN include/asm-x86_64/system.h~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch include/asm-x86_64/system.h --- devel/include/asm-x86_64/system.h~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch 2005-12-22 05:08:46.000000000 -0800 +++ devel-akpm/include/asm-x86_64/system.h 2005-12-22 05:08:46.000000000 -0800 @@ -311,11 +311,27 @@ static inline unsigned long __cmpxchg(vo /* interrupt control.. */ #define local_save_flags(x) do { warn_if_not_ulong(x); __asm__ __volatile__("# save_flags \n\t pushfq ; popq %q0":"=g" (x): /* no input */ :"memory"); } while (0) #define local_irq_restore(x) __asm__ __volatile__("# restore_flags \n\t pushq %0 ; popfq": /* no output */ :"g" (x):"memory", "cc") -#define local_irq_disable() __asm__ __volatile__("cli": : :"memory") -#define local_irq_enable() __asm__ __volatile__("sti": : :"memory") /* used in the idle loop; sti takes one instruction cycle to complete */ #define safe_halt() __asm__ __volatile__("sti; hlt": : :"memory") +#ifdef CONFIG_X86_VSMP +/* Interrupt control for VSMP architecture */ +#define local_irq_disable() do { unsigned long flags; local_save_flags(flags); local_irq_restore((flags & ~(1 << 9)) | (1 << 18)); } while (0) +#define local_irq_enable() do { unsigned long flags; local_save_flags(flags); local_irq_restore((flags | (1 << 9)) & ~(1 << 18)); } while (0) + +#define irqs_disabled() \ +({ \ + unsigned long flags; \ + local_save_flags(flags); \ + (flags & (1<<18)) || !(flags & (1<<9)); \ +}) + +/* For spinlocks etc */ +#define local_irq_save(x) do { local_save_flags(x); local_irq_restore((x & ~(1 << 9)) | (1 << 18)); } while (0) +#else /* CONFIG_X86_VSMP */ +#define local_irq_disable() __asm__ __volatile__("cli": : :"memory") +#define local_irq_enable() __asm__ __volatile__("sti": : :"memory") + #define irqs_disabled() \ ({ \ unsigned long flags; \ @@ -325,6 +341,7 @@ static inline unsigned long __cmpxchg(vo /* For spinlocks etc */ #define local_irq_save(x) do { warn_if_not_ulong(x); __asm__ __volatile__("# local_irq_save \n\t pushfq ; popq %0 ; cli":"=g" (x): /* no input */ :"memory"); } while (0) +#endif void cpu_idle_wait(void); diff -puN include/linux/pci_ids.h~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch include/linux/pci_ids.h --- devel/include/linux/pci_ids.h~inclusion-of-scalemp-vsmp-architecture-patches-vsmp_arch 2005-12-22 05:08:46.000000000 -0800 +++ devel-akpm/include/linux/pci_ids.h 2005-12-22 05:08:46.000000000 -0800 @@ -2121,6 +2121,9 @@ #define PCI_DEVICE_ID_INTEL_IXP2800 0x9004 #define PCI_DEVICE_ID_INTEL_S21152BB 0xb152 +#define PCI_VENDOR_ID_SCALEMP 0x8686 +#define PCI_DEVICE_ID_SCALEMP_VSMP_CTL 0x1010 + #define PCI_VENDOR_ID_COMPUTONE 0x8e0e #define PCI_DEVICE_ID_COMPUTONE_IP2EX 0x0291 #define PCI_DEVICE_ID_COMPUTONE_PG 0x0302 _