[PATCH] x86_64: Inclusion of ScaleMP vSMP architecture patches - vsmp_arch

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 <kiran@scalemp.com>
Signed-off-by: Shai Fultheim <shai@scalemp.com>
Signed-off-by: Andi Kleen <ak@suse.de>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>

authored by Ravikiran G Thirumalai and committed by Linus Torvalds 79f12614 5fd63b30

+85
+18
arch/x86_64/Kconfig
··· 79 79 menu "Processor type and features" 80 80 81 81 choice 82 + prompt "Subarchitecture Type" 83 + default X86_PC 84 + 85 + config X86_PC 86 + bool "PC-compatible" 87 + help 88 + Choose this option if your computer is a standard PC or compatible. 89 + 90 + config X86_VSMP 91 + bool "Support for ScaleMP vSMP" 92 + help 93 + Support for ScaleMP vSMP systems. Say 'Y' here if this kernel is 94 + supposed to run on these EM64T-based machines. Only choose this option 95 + if you have one of these machines. 96 + 97 + endchoice 98 + 99 + choice 82 100 prompt "Processor family" 83 101 default MK8 84 102
+1
arch/x86_64/kernel/Makefile
··· 32 32 obj-$(CONFIG_SWIOTLB) += pci-swiotlb.o 33 33 obj-$(CONFIG_KPROBES) += kprobes.o 34 34 obj-$(CONFIG_X86_PM_TIMER) += pmtimer.o 35 + obj-$(CONFIG_X86_VSMP) += vsmp.o 35 36 36 37 obj-$(CONFIG_MODULES) += module.o 37 38
+45
arch/x86_64/kernel/vsmp.c
··· 1 + /* 2 + * vSMPowered(tm) systems specific initialization 3 + * Copyright (C) 2005 ScaleMP Inc. 4 + * 5 + * Use of this code is subject to the terms and conditions of the 6 + * GNU general public license version 2. See "COPYING" or 7 + * http://www.gnu.org/licenses/gpl.html 8 + * 9 + * Ravikiran Thirumalai <kiran@scalemp.com>, 10 + * Shai Fultheim <shai@scalemp.com> 11 + */ 12 + 13 + #include <linux/init.h> 14 + #include <linux/pci_ids.h> 15 + #include <linux/pci_regs.h> 16 + #include <asm/pci-direct.h> 17 + 18 + static int __init vsmp_init(void) 19 + { 20 + void *address; 21 + unsigned int cap, ctl; 22 + 23 + /* Check if we are running on a ScaleMP vSMP box */ 24 + if ((read_pci_config_16(0, 0x1f, 0, PCI_VENDOR_ID) != PCI_VENDOR_ID_SCALEMP) || 25 + (read_pci_config_16(0, 0x1f, 0, PCI_DEVICE_ID) != PCI_DEVICE_ID_SCALEMP_VSMP_CTL)) 26 + return 0; 27 + 28 + /* set vSMP magic bits to indicate vSMP capable kernel */ 29 + address = ioremap(read_pci_config(0, 0x1f, 0, PCI_BASE_ADDRESS_0), 8); 30 + cap = readl(address); 31 + ctl = readl(address + 4); 32 + printk("vSMP CTL: capabilities:0x%08x control:0x%08x\n", cap, ctl); 33 + if (cap & ctl & (1 << 4)) { 34 + /* Turn on vSMP IRQ fastpath handling (see system.h) */ 35 + ctl &= ~(1 << 4); 36 + writel(ctl, address + 4); 37 + ctl = readl(address + 4); 38 + printk("vSMP CTL: control set to:0x%08x\n", ctl); 39 + } 40 + 41 + iounmap(address); 42 + return 0; 43 + } 44 + 45 + core_initcall(vsmp_init);
+18
include/asm-x86_64/system.h
··· 326 326 /* interrupt control.. */ 327 327 #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) 328 328 #define local_irq_restore(x) __asm__ __volatile__("# restore_flags \n\t pushq %0 ; popfq": /* no output */ :"g" (x):"memory", "cc") 329 + 330 + #ifdef CONFIG_X86_VSMP 331 + /* Interrupt control for VSMP architecture */ 332 + #define local_irq_disable() do { unsigned long flags; local_save_flags(flags); local_irq_restore((flags & ~(1 << 9)) | (1 << 18)); } while (0) 333 + #define local_irq_enable() do { unsigned long flags; local_save_flags(flags); local_irq_restore((flags | (1 << 9)) & ~(1 << 18)); } while (0) 334 + 335 + #define irqs_disabled() \ 336 + ({ \ 337 + unsigned long flags; \ 338 + local_save_flags(flags); \ 339 + (flags & (1<<18)) || !(flags & (1<<9)); \ 340 + }) 341 + 342 + /* For spinlocks etc */ 343 + #define local_irq_save(x) do { local_save_flags(x); local_irq_restore((x & ~(1 << 9)) | (1 << 18)); } while (0) 344 + #else /* CONFIG_X86_VSMP */ 329 345 #define local_irq_disable() __asm__ __volatile__("cli": : :"memory") 330 346 #define local_irq_enable() __asm__ __volatile__("sti": : :"memory") 347 + 331 348 /* used in the idle loop; sti takes one instruction cycle to complete */ 332 349 #define safe_halt() __asm__ __volatile__("sti; hlt": : :"memory") 333 350 /* used when interrupts are already enabled or to shutdown the processor */ ··· 359 342 360 343 /* For spinlocks etc */ 361 344 #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) 345 + #endif 362 346 363 347 void cpu_idle_wait(void); 364 348
+3
include/linux/pci_ids.h
··· 2152 2152 #define PCI_DEVICE_ID_INTEL_IXP2800 0x9004 2153 2153 #define PCI_DEVICE_ID_INTEL_S21152BB 0xb152 2154 2154 2155 + #define PCI_VENDOR_ID_SCALEMP 0x8686 2156 + #define PCI_DEVICE_ID_SCALEMP_VSMP_CTL 0x1010 2157 + 2155 2158 #define PCI_VENDOR_ID_COMPUTONE 0x8e0e 2156 2159 #define PCI_DEVICE_ID_COMPUTONE_IP2EX 0x0291 2157 2160 #define PCI_DEVICE_ID_COMPUTONE_PG 0x0302