1ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner/* 2ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * This file is subject to the terms and conditions of the GNU General Public 3ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * License. See the file "COPYING" in the main directory of this archive 4ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * for more details. 5ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * 6ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * SGI UV APIC functions (note: not an Intel compatible APIC) 7ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * 8c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson * Copyright (C) 2007-2010 Silicon Graphics, Inc. All rights reserved. 9ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner */ 10ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner#include <linux/cpumask.h> 110b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/hardirq.h> 120b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/proc_fs.h> 130b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/threads.h> 140b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/kernel.h> 150b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/module.h> 16ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner#include <linux/string.h> 17ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner#include <linux/ctype.h> 18ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner#include <linux/sched.h> 197f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis#include <linux/timer.h> 205a0e3ad6af8660be21ca98a971cd00f331318c05Tejun Heo#include <linux/slab.h> 210b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/cpu.h> 220b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <linux/init.h> 2327229ca63269c1be0a710f074fa9de4024f283f1Jack Steiner#include <linux/io.h> 24841582ea9e29a8f757c30c5377ce649586ba793aMike Travis#include <linux/pci.h> 2578c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson#include <linux/kdebug.h> 26ca444564a947034557a85357b3911d067cac4b8fJean Delvare#include <linux/delay.h> 27818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman#include <linux/crash_dump.h> 280b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar 29ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner#include <asm/uv/uv_mmrs.h> 30ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner#include <asm/uv/uv_hub.h> 310b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <asm/current.h> 320b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <asm/pgtable.h> 337019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson#include <asm/uv/bios.h> 340b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <asm/uv/uv.h> 350b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <asm/apic.h> 360b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <asm/ipi.h> 370b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#include <asm/smp.h> 38fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner#include <asm/x86_init.h> 39818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman#include <asm/emergency-restart.h> 401d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner#include <asm/nmi.h> 411d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 421d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner/* BMC sets a bit this MMR non-zero before sending an NMI */ 431d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner#define UVH_NMI_MMR UVH_SCRATCH5 441d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner#define UVH_NMI_MMR_CLEAR (UVH_NMI_MMR + 8) 451d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner#define UV_NMI_PENDING_MASK (1UL << 63) 461d44e8288a0557c28c447d7e511f50d06ff93a34Jack SteinerDEFINE_PER_CPU(unsigned long, cpu_last_nmi_count); 47ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 48510b37258dfd61693ca6c039865c78bd996e3718Yinghai LuDEFINE_PER_CPU(int, x2apic_extra_bits); 49510b37258dfd61693ca6c039865c78bd996e3718Yinghai Lu 50841582ea9e29a8f757c30c5377ce649586ba793aMike Travis#define PR_DEVEL(fmt, args...) pr_devel("%s: " fmt, __func__, args) 51841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 521b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lustatic enum uv_system_type uv_system_type; 53fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steinerstatic u64 gru_start_paddr, gru_end_paddr; 54c8f730b1ab825f06733e1c074264f0078721f365Russ Andersonstatic union uvh_apicid uvh_apicid; 557a1110e861b2666ac09f5708d6fbe71d18ce64bbJack Steinerint uv_min_hub_revision_id; 567a1110e861b2666ac09f5708d6fbe71d18ce64bbJack SteinerEXPORT_SYMBOL_GPL(uv_min_hub_revision_id); 578191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanichunsigned int uv_apicid_hibits; 588191c9f69202d4dbc66063cb92059b8a58640d34Dimitri SivanichEXPORT_SYMBOL_GPL(uv_apicid_hibits); 5978c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Andersonstatic DEFINE_SPINLOCK(uv_nmi_lock); 60fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner 611a8880a14270814dae0d226a2ad065d30587e60aSuresh Siddhastatic struct apic apic_x2apic_uv_x; 621a8880a14270814dae0d226a2ad065d30587e60aSuresh Siddha 63e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steinerstatic unsigned long __init uv_early_read_mmr(unsigned long addr) 64e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner{ 65e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner unsigned long val, *mmr; 66e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner 67e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner mmr = early_ioremap(UV_LOCAL_MMR_BASE | addr, sizeof(*mmr)); 68e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner val = *mmr; 69e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner early_iounmap(mmr, sizeof(*mmr)); 70e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner return val; 71e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner} 72e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner 73eb41c8be89dbe079f49202774e04a79ccac48a09H. Peter Anvinstatic inline bool is_GRU_range(u64 start, u64 end) 74fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner{ 75ccef086454d4c97e7b722e9303390207d681cb4cH. Peter Anvin return start >= gru_start_paddr && end <= gru_end_paddr; 76fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner} 77fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner 78eb41c8be89dbe079f49202774e04a79ccac48a09H. Peter Anvinstatic bool uv_is_untracked_pat_range(u64 start, u64 end) 79fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner{ 80fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner return is_ISA_range(start, end) || is_GRU_range(start, end); 81fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner} 821b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu 83d8850ba425d9823d3184bd52f065899dac4689f9Jack Steinerstatic int __init early_get_pnodeid(void) 8427229ca63269c1be0a710f074fa9de4024f283f1Jack Steiner{ 8527229ca63269c1be0a710f074fa9de4024f283f1Jack Steiner union uvh_node_id_u node_id; 86d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner union uvh_rh_gam_config_mmr_u m_n_config; 87d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner int pnode; 887a1110e861b2666ac09f5708d6fbe71d18ce64bbJack Steiner 897a1110e861b2666ac09f5708d6fbe71d18ce64bbJack Steiner /* Currently, all blades have same revision number */ 90e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner node_id.v = uv_early_read_mmr(UVH_NODE_ID); 91d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner m_n_config.v = uv_early_read_mmr(UVH_RH_GAM_CONFIG_MMR); 927a1110e861b2666ac09f5708d6fbe71d18ce64bbJack Steiner uv_min_hub_revision_id = node_id.s.revision; 937a1110e861b2666ac09f5708d6fbe71d18ce64bbJack Steiner 942a919596c16b4333af851ff473ebf96e289ab90cJack Steiner if (node_id.s.part_number == UV2_HUB_PART_NUMBER) 952a919596c16b4333af851ff473ebf96e289ab90cJack Steiner uv_min_hub_revision_id += UV2_HUB_REVISION_BASE - 1; 96b495e039b4ce2ce4a96b3006004faf082f4d50e2Jack Steiner if (node_id.s.part_number == UV2_HUB_PART_NUMBER_X) 97b495e039b4ce2ce4a96b3006004faf082f4d50e2Jack Steiner uv_min_hub_revision_id += UV2_HUB_REVISION_BASE - 1; 982a919596c16b4333af851ff473ebf96e289ab90cJack Steiner 992a919596c16b4333af851ff473ebf96e289ab90cJack Steiner uv_hub_info->hub_revision = uv_min_hub_revision_id; 100d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner pnode = (node_id.s.node_id >> 1) & ((1 << m_n_config.s.n_skt) - 1); 101d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner return pnode; 10227229ca63269c1be0a710f074fa9de4024f283f1Jack Steiner} 10327229ca63269c1be0a710f074fa9de4024f283f1Jack Steiner 1040520bd8438f18f2b1b2af5fd1c4ecc070a1bf837Russ Andersonstatic void __init early_get_apic_pnode_shift(void) 105c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson{ 106e681041388e61ecd7f99dba66b3c1db11a564d92Jack Steiner uvh_apicid.v = uv_early_read_mmr(UVH_APICID); 107c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson if (!uvh_apicid.v) 108c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson /* 109c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson * Old bios, use default value 110c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson */ 111c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson uvh_apicid.s.pnode_shift = UV_APIC_PNODE_SHIFT; 112c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson} 113c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson 1148191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich/* 1158191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich * Add an extra bit as dictated by bios to the destination apicid of 1168191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich * interrupts potentially passing through the UV HUB. This prevents 1178191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich * a deadlock between interrupts and IO port operations. 1188191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich */ 1198191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanichstatic void __init uv_set_apicid_hibit(void) 1208191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich{ 1212a919596c16b4333af851ff473ebf96e289ab90cJack Steiner union uv1h_lb_target_physical_apic_id_mask_u apicid_mask; 1228191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich 1232a919596c16b4333af851ff473ebf96e289ab90cJack Steiner if (is_uv1_hub()) { 1242a919596c16b4333af851ff473ebf96e289ab90cJack Steiner apicid_mask.v = 1252a919596c16b4333af851ff473ebf96e289ab90cJack Steiner uv_early_read_mmr(UV1H_LB_TARGET_PHYSICAL_APIC_ID_MASK); 1262a919596c16b4333af851ff473ebf96e289ab90cJack Steiner uv_apicid_hibits = 1272a919596c16b4333af851ff473ebf96e289ab90cJack Steiner apicid_mask.s1.bit_enables & UV_APICID_HIBIT_MASK; 1282a919596c16b4333af851ff473ebf96e289ab90cJack Steiner } 1298191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich} 1308191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich 13152459ab91363343af8ae252766e9da762344a2e7Leonardo Potenzastatic int __init uv_acpi_madt_oem_check(char *oem_id, char *oem_table_id) 1321b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu{ 1332a919596c16b4333af851ff473ebf96e289ab90cJack Steiner int pnodeid, is_uv1, is_uv2; 1341d2c867c941d635e53e8ad7bf37d060bb5b25ec5Russ Anderson 1352a919596c16b4333af851ff473ebf96e289ab90cJack Steiner is_uv1 = !strcmp(oem_id, "SGI"); 1362a919596c16b4333af851ff473ebf96e289ab90cJack Steiner is_uv2 = !strcmp(oem_id, "SGI2"); 1372a919596c16b4333af851ff473ebf96e289ab90cJack Steiner if (is_uv1 || is_uv2) { 1382a919596c16b4333af851ff473ebf96e289ab90cJack Steiner uv_hub_info->hub_revision = 1392a919596c16b4333af851ff473ebf96e289ab90cJack Steiner is_uv1 ? UV1_HUB_REVISION_BASE : UV2_HUB_REVISION_BASE; 140d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner pnodeid = early_get_pnodeid(); 1410520bd8438f18f2b1b2af5fd1c4ecc070a1bf837Russ Anderson early_get_apic_pnode_shift(); 142fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner x86_platform.is_untracked_pat_range = uv_is_untracked_pat_range; 14378c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson x86_platform.nmi_init = uv_nmi_init; 1441b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu if (!strcmp(oem_table_id, "UVL")) 1451b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu uv_system_type = UV_LEGACY_APIC; 1461b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu else if (!strcmp(oem_table_id, "UVX")) 1471b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu uv_system_type = UV_X2APIC; 1481b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu else if (!strcmp(oem_table_id, "UVH")) { 1490a3aee0da4402aa19b66e458038533c896fb80c6Tejun Heo __this_cpu_write(x2apic_extra_bits, 15072eb6a791459c87a0340318840bb3bd9252b627bLinus Torvalds pnodeid << uvh_apicid.s.pnode_shift); 1511b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu uv_system_type = UV_NON_UNIQUE_APIC; 1528191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich uv_set_apicid_hibit(); 1531b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu return 1; 1541b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu } 1551b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu } 1561b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu return 0; 1571b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu} 1581b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu 1591b9b89e7f163336ad84200b66a17284dbf26acedYinghai Luenum uv_system_type get_uv_system_type(void) 1601b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu{ 1611b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu return uv_system_type; 1621b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu} 1631b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu 1641b9b89e7f163336ad84200b66a17284dbf26acedYinghai Luint is_uv_system(void) 1651b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu{ 1661b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu return uv_system_type != UV_NONE; 1671b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu} 1688067794bec1cc5de1431102cf0a6a1c7ce75cd85Ingo MolnarEXPORT_SYMBOL_GPL(is_uv_system); 1691b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lu 170ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack SteinerDEFINE_PER_CPU(struct uv_hub_info_s, __uv_hub_info); 171ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack SteinerEXPORT_PER_CPU_SYMBOL_GPL(__uv_hub_info); 172ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 173ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinerstruct uv_blade_info *uv_blade_info; 174ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack SteinerEXPORT_SYMBOL_GPL(uv_blade_info); 175ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 176ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinershort *uv_node_to_blade; 177ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack SteinerEXPORT_SYMBOL_GPL(uv_node_to_blade); 178ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 179ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinershort *uv_cpu_to_blade; 180ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack SteinerEXPORT_SYMBOL_GPL(uv_cpu_to_blade); 181ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 182ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinershort uv_possible_blades; 183ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack SteinerEXPORT_SYMBOL_GPL(uv_possible_blades); 184ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 1857019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Andersonunsigned long sn_rtc_cycles_per_second; 1867019cc2dd6fafcdc6b104005482dc910dcdbb797Russ AndersonEXPORT_SYMBOL(sn_rtc_cycles_per_second); 1877019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson 188bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travisstatic const struct cpumask *uv_target_cpus(void) 189ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 1908447b360a3897bdfb0677107564d1dd9ab6e63beJack Steiner return cpu_online_mask; 191ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 192ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 193bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travisstatic void uv_vector_allocation_domain(int cpu, struct cpumask *retmask) 194ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 195bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travis cpumask_clear(retmask); 196bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travis cpumask_set_cpu(cpu, retmask); 197ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 198ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 199667c5296cc76fefe0abcb79228952b28d9af45e3Cyrill Gorcunovstatic int __cpuinit uv_wakeup_secondary(int phys_apicid, unsigned long start_rip) 200ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 2010b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#ifdef CONFIG_SMP 202ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner unsigned long val; 2039f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner int pnode; 204ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 2059f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner pnode = uv_apicid_to_pnode(phys_apicid); 2068191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich phys_apicid |= uv_apicid_hibits; 207ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner val = (1UL << UVH_IPI_INT_SEND_SHFT) | 208ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner (phys_apicid << UVH_IPI_INT_APIC_ID_SHFT) | 2092b6163bf5772644068694583816fa41e8474239fYinghai Lu ((start_rip << UVH_IPI_INT_VECTOR_SHFT) >> 12) | 21034d0559178393547505ec9492321255405f4e441Jack Steiner APIC_DM_INIT; 2119f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_write_global_mmr64(pnode, UVH_IPI_INT, val); 21234d0559178393547505ec9492321255405f4e441Jack Steiner 21334d0559178393547505ec9492321255405f4e441Jack Steiner val = (1UL << UVH_IPI_INT_SEND_SHFT) | 21434d0559178393547505ec9492321255405f4e441Jack Steiner (phys_apicid << UVH_IPI_INT_APIC_ID_SHFT) | 2152b6163bf5772644068694583816fa41e8474239fYinghai Lu ((start_rip << UVH_IPI_INT_VECTOR_SHFT) >> 12) | 21634d0559178393547505ec9492321255405f4e441Jack Steiner APIC_DM_STARTUP; 2179f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_write_global_mmr64(pnode, UVH_IPI_INT, val); 2182b6163bf5772644068694583816fa41e8474239fYinghai Lu 2192b6163bf5772644068694583816fa41e8474239fYinghai Lu atomic_set(&init_deasserted, 1); 2200b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar#endif 221ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner return 0; 222ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 223ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 224ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinerstatic void uv_send_IPI_one(int cpu, int vector) 225ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 22666666e50fcd69d80117d7d243ce02e1f774cbaf5Jack Steiner unsigned long apicid; 2279f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner int pnode; 228ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 2291e0b5d00b230ceffe1bb33284b46b8572e418423Jack Steiner apicid = per_cpu(x86_cpu_to_apicid, cpu); 2309f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner pnode = uv_apicid_to_pnode(apicid); 23166666e50fcd69d80117d7d243ce02e1f774cbaf5Jack Steiner uv_hub_send_ipi(pnode, apicid, vector); 232ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 233ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 234bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travisstatic void uv_send_IPI_mask(const struct cpumask *mask, int vector) 235ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 236ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner unsigned int cpu; 237ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 238bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travis for_each_cpu(cpu, mask) 239e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis uv_send_IPI_one(cpu, vector); 240e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis} 241e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis 242bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travisstatic void uv_send_IPI_mask_allbutself(const struct cpumask *mask, int vector) 243e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis{ 244e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis unsigned int this_cpu = smp_processor_id(); 245dac5f4121df3c39fdb2ea57acd669a0ae19e46f8Ingo Molnar unsigned int cpu; 246e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis 247dac5f4121df3c39fdb2ea57acd669a0ae19e46f8Ingo Molnar for_each_cpu(cpu, mask) { 248e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis if (cpu != this_cpu) 249ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_send_IPI_one(cpu, vector); 250dac5f4121df3c39fdb2ea57acd669a0ae19e46f8Ingo Molnar } 251ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 252ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 253ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinerstatic void uv_send_IPI_allbutself(int vector) 254ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 255e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis unsigned int this_cpu = smp_processor_id(); 256dac5f4121df3c39fdb2ea57acd669a0ae19e46f8Ingo Molnar unsigned int cpu; 257ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 258dac5f4121df3c39fdb2ea57acd669a0ae19e46f8Ingo Molnar for_each_online_cpu(cpu) { 259e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis if (cpu != this_cpu) 260e7986739a76cde5079da08809d8bbc6878387ae0Mike Travis uv_send_IPI_one(cpu, vector); 261dac5f4121df3c39fdb2ea57acd669a0ae19e46f8Ingo Molnar } 262ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 263ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 264ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinerstatic void uv_send_IPI_all(int vector) 265ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 266bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travis uv_send_IPI_mask(cpu_online_mask, vector); 267ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 268ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 269b7157acf429e6aef690646ba964b9ebd25049ec2Steffen Persvoldstatic int uv_apic_id_valid(int apicid) 270b7157acf429e6aef690646ba964b9ebd25049ec2Steffen Persvold{ 271b7157acf429e6aef690646ba964b9ebd25049ec2Steffen Persvold return 1; 272b7157acf429e6aef690646ba964b9ebd25049ec2Steffen Persvold} 273b7157acf429e6aef690646ba964b9ebd25049ec2Steffen Persvold 274ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinerstatic int uv_apic_id_registered(void) 275ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 276ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner return 1; 277ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 278ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 279277d1f5846d84e16760131a93b7a67ebfa8eded4Suresh Siddhastatic void uv_init_apic_ldr(void) 2805c520a6724e912a7e6153b7597192edad6752750Suresh Siddha{ 2815c520a6724e912a7e6153b7597192edad6752750Suresh Siddha} 2825c520a6724e912a7e6153b7597192edad6752750Suresh Siddha 283bcda016eddd7a8b374bb371473c821a91ff1d8ccMike Travisstatic unsigned int uv_cpu_mask_to_apicid(const struct cpumask *cpumask) 284ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 285ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner /* 286ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * We're using fixed IRQ delivery, can only return one phys APIC ID. 287ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * May as well be the first. 288ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner */ 289debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnar int cpu = cpumask_first(cpumask); 290debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnar 291247bc6ca0f691e4617e7bdb70cbaccc939f754ecMike Travis if ((unsigned)cpu < nr_cpu_ids) 2928191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich return per_cpu(x86_cpu_to_apicid, cpu) | uv_apicid_hibits; 293ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner else 294ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner return BAD_APICID; 295ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 296ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 297debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnarstatic unsigned int 298debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnaruv_cpu_mask_to_apicid_and(const struct cpumask *cpumask, 299debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnar const struct cpumask *andmask) 30095d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis{ 30195d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis int cpu; 30295d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis 30395d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis /* 30495d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis * We're using fixed IRQ delivery, can only return one phys APIC ID. 30595d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis * May as well be the first. 30695d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis */ 307debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnar for_each_cpu_and(cpu, cpumask, andmask) { 308a775a38b1353161a6d7af86b667d6523c12c1a37Mike Travis if (cpumask_test_cpu(cpu, cpu_online_mask)) 309a775a38b1353161a6d7af86b667d6523c12c1a37Mike Travis break; 310debccb3e77be52cfc26c5a99e123c114c5c72aebIngo Molnar } 3118191c9f69202d4dbc66063cb92059b8a58640d34Dimitri Sivanich return per_cpu(x86_cpu_to_apicid, cpu) | uv_apicid_hibits; 31295d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis} 31395d313cf1c1ecedc8bec5727b09bdacbf67dfc45Mike Travis 314ca6c8ed4646f8ccaa4f7db618bf69b8b8fb49767Ingo Molnarstatic unsigned int x2apic_get_apic_id(unsigned long x) 3150c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha{ 3160c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha unsigned int id; 3170c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha 3180c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha WARN_ON(preemptible() && num_online_cpus() > 1); 3190a3aee0da4402aa19b66e458038533c896fb80c6Tejun Heo id = x | __this_cpu_read(x2apic_extra_bits); 3200c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha 3210c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha return id; 3220c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha} 3230c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha 3241b9b89e7f163336ad84200b66a17284dbf26acedYinghai Lustatic unsigned long set_apic_id(unsigned int id) 325f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu{ 326f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu unsigned long x; 327f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu 328f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu /* maskout x2apic_extra_bits ? */ 329f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu x = id; 330f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu return x; 331f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu} 332f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu 333f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lustatic unsigned int uv_read_apic_id(void) 334f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu{ 335f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu 336ca6c8ed4646f8ccaa4f7db618bf69b8b8fb49767Ingo Molnar return x2apic_get_apic_id(apic_read(APIC_ID)); 337f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu} 338f910a9dc7c865896815e2a95fe33363e9522f277Yinghai Lu 339d4c9a9f3d416cfa1f5ffbe09d864d069467fe693Ingo Molnarstatic int uv_phys_pkg_id(int initial_apicid, int index_msb) 340ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 3410c81c746f9bdbfaafe64322d540c8b7b59c27314Suresh Siddha return uv_read_apic_id() >> index_msb; 342ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 343ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 344ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steinerstatic void uv_send_IPI_self(int vector) 345ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 346ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner apic_write(APIC_SELF_IPI, vector); 347ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 348ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 3499ebd680bd029a9fc47399ca61c950f8b6730ac40Suresh Siddhastatic int uv_probe(void) 3509ebd680bd029a9fc47399ca61c950f8b6730ac40Suresh Siddha{ 3519ebd680bd029a9fc47399ca61c950f8b6730ac40Suresh Siddha return apic == &apic_x2apic_uv_x; 3529ebd680bd029a9fc47399ca61c950f8b6730ac40Suresh Siddha} 3539ebd680bd029a9fc47399ca61c950f8b6730ac40Suresh Siddha 3541a8880a14270814dae0d226a2ad065d30587e60aSuresh Siddhastatic struct apic __refdata apic_x2apic_uv_x = { 355c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 356c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .name = "UV large system", 3579ebd680bd029a9fc47399ca61c950f8b6730ac40Suresh Siddha .probe = uv_probe, 358c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .acpi_madt_oem_check = uv_acpi_madt_oem_check, 359b7157acf429e6aef690646ba964b9ebd25049ec2Steffen Persvold .apic_id_valid = uv_apic_id_valid, 360c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .apic_id_registered = uv_apic_id_registered, 361c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 362f8987a1093cc7a896137e264c24e04d4048e9f95Ingo Molnar .irq_delivery_mode = dest_Fixed, 363c5997fa8d7aca3c9876a6ff71bacf27c41095ce9Jack Steiner .irq_dest_mode = 0, /* physical */ 364c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 365c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .target_cpus = uv_target_cpus, 36608125d3edab90644724652eedec3e219e3e0f2e7Ingo Molnar .disable_esr = 0, 367bdb1a9b62fc182d4da3143e346f7a0925d243352Ingo Molnar .dest_logical = APIC_DEST_LOGICAL, 368c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .check_apicid_used = NULL, 369c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .check_apicid_present = NULL, 370c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 371c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .vector_allocation_domain = uv_vector_allocation_domain, 372c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .init_apic_ldr = uv_init_apic_ldr, 373c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 374c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .ioapic_phys_id_map = NULL, 375c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .setup_apic_routing = NULL, 376c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .multi_timer_check = NULL, 377a21769a4461801454930a06bc18bd8249cd9e993Ingo Molnar .cpu_present_to_apicid = default_cpu_present_to_apicid, 378c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .apicid_to_cpu_present = NULL, 379c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .setup_portio_remap = NULL, 380a27a621001f4c3e57caf47feff4b014577fd01c6Ingo Molnar .check_phys_apicid_present = default_check_phys_apicid_present, 381c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .enable_apic_mode = NULL, 382d4c9a9f3d416cfa1f5ffbe09d864d069467fe693Ingo Molnar .phys_pkg_id = uv_phys_pkg_id, 383c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .mps_oem_check = NULL, 384c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 385ca6c8ed4646f8ccaa4f7db618bf69b8b8fb49767Ingo Molnar .get_apic_id = x2apic_get_apic_id, 386c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .set_apic_id = set_apic_id, 387c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .apic_id_mask = 0xFFFFFFFFu, 388c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 389c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .cpu_mask_to_apicid = uv_cpu_mask_to_apicid, 390c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .cpu_mask_to_apicid_and = uv_cpu_mask_to_apicid_and, 391c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 392c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .send_IPI_mask = uv_send_IPI_mask, 393c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .send_IPI_mask_allbutself = uv_send_IPI_mask_allbutself, 394c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .send_IPI_allbutself = uv_send_IPI_allbutself, 395c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .send_IPI_all = uv_send_IPI_all, 396c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .send_IPI_self = uv_send_IPI_self, 397c7967329911013a05920ef12832935c541bb8c9aIngo Molnar 3981f5bcabf1b997d6b76a09114b5a79423495a1263Ingo Molnar .wakeup_secondary_cpu = uv_wakeup_secondary, 399abfa584c8df8b691cf18f51c7d4af27e5b32be4aIngo Molnar .trampoline_phys_low = DEFAULT_TRAMPOLINE_PHYS_LOW, 400abfa584c8df8b691cf18f51c7d4af27e5b32be4aIngo Molnar .trampoline_phys_high = DEFAULT_TRAMPOLINE_PHYS_HIGH, 401c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .wait_for_init_deassert = NULL, 402c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .smp_callin_clear_local_apic = NULL, 403c7967329911013a05920ef12832935c541bb8c9aIngo Molnar .inquire_remote_apic = NULL, 404c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu 405c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu .read = native_apic_msr_read, 406c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu .write = native_apic_msr_write, 407c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu .icr_read = native_x2apic_icr_read, 408c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu .icr_write = native_x2apic_icr_write, 409c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu .wait_icr_idle = native_x2apic_wait_icr_idle, 410c1eeb2de41d7015678bdd412b48a5f071b84e29aYinghai Lu .safe_wait_icr_idle = native_safe_x2apic_wait_icr_idle, 411ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner}; 412ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 4139f5314fb4d556d3132c784d0df47352b2830ca53Jack Steinerstatic __cpuinit void set_x2apic_extra_bits(int pnode) 414ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 41516ee8db6a93ffbc021132599f33288613f042c3dLinus Torvalds __this_cpu_write(x2apic_extra_bits, pnode << uvh_apicid.s.pnode_shift); 416ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 417ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 418ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner/* 419ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner * Called on boot cpu. 420ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner */ 4219f5314fb4d556d3132c784d0df47352b2830ca53Jack Steinerstatic __init int boot_pnode_to_blade(int pnode) 4229f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner{ 4239f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner int blade; 4249f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 4259f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner for (blade = 0; blade < uv_num_possible_blades(); blade++) 4269f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner if (pnode == uv_blade_info[blade].pnode) 4279f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner return blade; 4289f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner BUG(); 4299f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner} 4309f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 4319f5314fb4d556d3132c784d0df47352b2830ca53Jack Steinerstruct redir_addr { 4329f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner unsigned long redirect; 4339f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner unsigned long alias; 4349f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner}; 4359f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 4369f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner#define DEST_SHIFT UVH_RH_GAM_ALIAS210_REDIRECT_CONFIG_0_MMR_DEST_BASE_SHFT 4379f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 4389f5314fb4d556d3132c784d0df47352b2830ca53Jack Steinerstatic __initdata struct redir_addr redir_addrs[] = { 43962b0cfc240b1d4601333912ef8760e0ca9ec2cecJack Steiner {UVH_RH_GAM_ALIAS210_REDIRECT_CONFIG_0_MMR, UVH_RH_GAM_ALIAS210_OVERLAY_CONFIG_0_MMR}, 44062b0cfc240b1d4601333912ef8760e0ca9ec2cecJack Steiner {UVH_RH_GAM_ALIAS210_REDIRECT_CONFIG_1_MMR, UVH_RH_GAM_ALIAS210_OVERLAY_CONFIG_1_MMR}, 44162b0cfc240b1d4601333912ef8760e0ca9ec2cecJack Steiner {UVH_RH_GAM_ALIAS210_REDIRECT_CONFIG_2_MMR, UVH_RH_GAM_ALIAS210_OVERLAY_CONFIG_2_MMR}, 4429f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner}; 4439f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 4449f5314fb4d556d3132c784d0df47352b2830ca53Jack Steinerstatic __init void get_lowmem_redirect(unsigned long *base, unsigned long *size) 4459f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner{ 44662b0cfc240b1d4601333912ef8760e0ca9ec2cecJack Steiner union uvh_rh_gam_alias210_overlay_config_2_mmr_u alias; 4479f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner union uvh_rh_gam_alias210_redirect_config_2_mmr_u redirect; 4489f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner int i; 4499f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 4509f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner for (i = 0; i < ARRAY_SIZE(redir_addrs); i++) { 4519f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner alias.v = uv_read_local_mmr(redir_addrs[i].alias); 452036ed8ba61b72c19dc5759446d4fe0844aa88255Robin Holt if (alias.s.enable && alias.s.base == 0) { 4539f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner *size = (1UL << alias.s.m_alias); 4549f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner redirect.v = uv_read_local_mmr(redir_addrs[i].redirect); 4559f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner *base = (unsigned long)redirect.s.dest_base << DEST_SHIFT; 4569f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner return; 4579f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner } 4589f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner } 459036ed8ba61b72c19dc5759446d4fe0844aa88255Robin Holt *base = *size = 0; 4609f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner} 4619f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 46283f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steinerenum map_type {map_wb, map_uc}; 46383f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 464fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travisstatic __init void map_high(char *id, unsigned long base, int pshift, 465fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travis int bshift, int max_pnode, enum map_type map_type) 46683f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner{ 46783f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner unsigned long bytes, paddr; 46883f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 469fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travis paddr = base << pshift; 470fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travis bytes = (1UL << bshift) * (max_pnode + 1); 47183f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner printk(KERN_INFO "UV: Map %s_HI 0x%lx - 0x%lx\n", id, paddr, 4720b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar paddr + bytes); 47383f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner if (map_type == map_uc) 47483f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner init_extra_mapping_uc(paddr, bytes); 47583f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner else 47683f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner init_extra_mapping_wb(paddr, bytes); 47783f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 47883f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner} 47983f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steinerstatic __init void map_gru_high(int max_pnode) 48083f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner{ 48183f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner union uvh_rh_gam_gru_overlay_config_mmr_u gru; 48283f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner int shift = UVH_RH_GAM_GRU_OVERLAY_CONFIG_MMR_BASE_SHFT; 48383f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 48483f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner gru.v = uv_read_local_mmr(UVH_RH_GAM_GRU_OVERLAY_CONFIG_MMR); 485fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner if (gru.s.enable) { 486fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travis map_high("GRU", gru.s.base, shift, shift, max_pnode, map_wb); 487fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner gru_start_paddr = ((u64)gru.s.base << shift); 488fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner gru_end_paddr = gru_start_paddr + (1UL << shift) * (max_pnode + 1); 489fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner 490fd12a0d69aee6d90fa9b9890db24368a897f8423Jack Steiner } 49183f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner} 49283f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 493daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steinerstatic __init void map_mmr_high(int max_pnode) 494daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner{ 495daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner union uvh_rh_gam_mmr_overlay_config_mmr_u mmr; 496daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner int shift = UVH_RH_GAM_MMR_OVERLAY_CONFIG_MMR_BASE_SHFT; 497daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner 498daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner mmr.v = uv_read_local_mmr(UVH_RH_GAM_MMR_OVERLAY_CONFIG_MMR); 499daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner if (mmr.s.enable) 500fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travis map_high("MMR", mmr.s.base, shift, shift, max_pnode, map_uc); 501daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner} 502daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner 50383f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steinerstatic __init void map_mmioh_high(int max_pnode) 50483f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner{ 50583f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner union uvh_rh_gam_mmioh_overlay_config_mmr_u mmioh; 5062a919596c16b4333af851ff473ebf96e289ab90cJack Steiner int shift; 50783f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 50883f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner mmioh.v = uv_read_local_mmr(UVH_RH_GAM_MMIOH_OVERLAY_CONFIG_MMR); 5092a919596c16b4333af851ff473ebf96e289ab90cJack Steiner if (is_uv1_hub() && mmioh.s1.enable) { 5102a919596c16b4333af851ff473ebf96e289ab90cJack Steiner shift = UV1H_RH_GAM_MMIOH_OVERLAY_CONFIG_MMR_BASE_SHFT; 5112a919596c16b4333af851ff473ebf96e289ab90cJack Steiner map_high("MMIOH", mmioh.s1.base, shift, mmioh.s1.m_io, 5122a919596c16b4333af851ff473ebf96e289ab90cJack Steiner max_pnode, map_uc); 5132a919596c16b4333af851ff473ebf96e289ab90cJack Steiner } 5142a919596c16b4333af851ff473ebf96e289ab90cJack Steiner if (is_uv2_hub() && mmioh.s2.enable) { 5152a919596c16b4333af851ff473ebf96e289ab90cJack Steiner shift = UV2H_RH_GAM_MMIOH_OVERLAY_CONFIG_MMR_BASE_SHFT; 5162a919596c16b4333af851ff473ebf96e289ab90cJack Steiner map_high("MMIOH", mmioh.s2.base, shift, mmioh.s2.m_io, 517fcfbb2b5facd65efa7284cc315225bfe3d1856c2Mike Travis max_pnode, map_uc); 5182a919596c16b4333af851ff473ebf96e289ab90cJack Steiner } 51983f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner} 52083f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 521918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steinerstatic __init void map_low_mmrs(void) 522918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner{ 523918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner init_extra_mapping_uc(UV_GLOBAL_MMR32_BASE, UV_GLOBAL_MMR32_SIZE); 524918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner init_extra_mapping_uc(UV_LOCAL_MMR_BASE, UV_LOCAL_MMR_SIZE); 525918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner} 526918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner 5277019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Andersonstatic __init void uv_rtc_init(void) 5287019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson{ 529922402f15a85f7a064926eb1db68cc52bc4d4a91Russ Anderson long status; 530922402f15a85f7a064926eb1db68cc52bc4d4a91Russ Anderson u64 ticks_per_sec; 5317019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson 532922402f15a85f7a064926eb1db68cc52bc4d4a91Russ Anderson status = uv_bios_freq_base(BIOS_FREQ_BASE_REALTIME_CLOCK, 533922402f15a85f7a064926eb1db68cc52bc4d4a91Russ Anderson &ticks_per_sec); 534922402f15a85f7a064926eb1db68cc52bc4d4a91Russ Anderson if (status != BIOS_STATUS_SUCCESS || ticks_per_sec < 100000) { 5357019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson printk(KERN_WARNING 5367019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson "unable to determine platform RTC clock frequency, " 5377019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson "guessing.\n"); 5387019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson /* BIOS gives wrong value for clock freq. so guess */ 5397019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson sn_rtc_cycles_per_second = 1000000000000UL / 30000UL; 5407019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson } else 5417019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson sn_rtc_cycles_per_second = ticks_per_sec; 5427019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson} 5437019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson 5448da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner/* 5457f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis * percpu heartbeat timer 5467f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis */ 5477f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic void uv_heartbeat(unsigned long ignored) 5487f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 5497f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis struct timer_list *timer = &uv_hub_info->scir.timer; 5507f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis unsigned char bits = uv_hub_info->scir.state; 5517f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 5527f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis /* flip heartbeat bit */ 5537f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis bits ^= SCIR_CPU_HEARTBEAT; 5547f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 55569a72a0e9337aad8c730e8e9942d5aa022bc4c5cMike Travis /* is this cpu idle? */ 55669a72a0e9337aad8c730e8e9942d5aa022bc4c5cMike Travis if (idle_cpu(raw_smp_processor_id())) 5577f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis bits &= ~SCIR_CPU_ACTIVITY; 5587f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis else 5597f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis bits |= SCIR_CPU_ACTIVITY; 5607f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 5617f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis /* update system controller interface reg */ 5627f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_set_scir_bits(bits); 5637f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 5647f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis /* enable next timer period */ 5655c333864a6ba811052d52ef14fbed056b9ac3512Arun R Bharadwaj mod_timer_pinned(timer, jiffies + SCIR_CPU_HB_INTERVAL); 5667f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 5677f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 5687f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic void __cpuinit uv_heartbeat_enable(int cpu) 5697f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 57099659a929d653d0c9ce458091870544768add871Roel Kluin while (!uv_cpu_hub_info(cpu)->scir.enabled) { 5717f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis struct timer_list *timer = &uv_cpu_hub_info(cpu)->scir.timer; 5727f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 5737f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_set_cpu_scir_bits(cpu, SCIR_CPU_HEARTBEAT|SCIR_CPU_ACTIVITY); 5747f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis setup_timer(timer, uv_heartbeat, cpu); 5757f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis timer->expires = jiffies + SCIR_CPU_HB_INTERVAL; 5767f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis add_timer_on(timer, cpu); 5777f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_cpu_hub_info(cpu)->scir.enabled = 1; 5787f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 57999659a929d653d0c9ce458091870544768add871Roel Kluin /* also ensure that boot cpu is enabled */ 58099659a929d653d0c9ce458091870544768add871Roel Kluin cpu = 0; 58199659a929d653d0c9ce458091870544768add871Roel Kluin } 5827f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 5837f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 58477be80e437fec44f8b7a620314b7d7b605b8d93bRichard A. Holden III#ifdef CONFIG_HOTPLUG_CPU 5857f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic void __cpuinit uv_heartbeat_disable(int cpu) 5867f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 5877f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis if (uv_cpu_hub_info(cpu)->scir.enabled) { 5887f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_cpu_hub_info(cpu)->scir.enabled = 0; 5897f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis del_timer(&uv_cpu_hub_info(cpu)->scir.timer); 5907f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis } 5917f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_set_cpu_scir_bits(cpu, 0xff); 5927f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 5937f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 5947f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis/* 5957f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis * cpu hotplug notifier 5967f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis */ 5977f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic __cpuinit int uv_scir_cpu_notify(struct notifier_block *self, 5987f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis unsigned long action, void *hcpu) 5997f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 6007f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis long cpu = (long)hcpu; 6017f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6027f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis switch (action) { 6037f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis case CPU_ONLINE: 6047f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_heartbeat_enable(cpu); 6057f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis break; 6067f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis case CPU_DOWN_PREPARE: 6077f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_heartbeat_disable(cpu); 6087f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis break; 6097f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis default: 6107f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis break; 6117f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis } 6127f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis return NOTIFY_OK; 6137f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 6147f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6157f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic __init void uv_scir_register_cpu_notifier(void) 6167f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 6177f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis hotcpu_notifier(uv_scir_cpu_notify, 0); 6187f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 6197f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6207f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis#else /* !CONFIG_HOTPLUG_CPU */ 6217f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6227f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic __init void uv_scir_register_cpu_notifier(void) 6237f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 6247f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 6257f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6267f1baa063e2582dd52d83bb31508e9e84468c666Mike Travisstatic __init int uv_init_heartbeat(void) 6277f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis{ 6287f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis int cpu; 6297f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6307f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis if (is_uv_system()) 6317f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis for_each_online_cpu(cpu) 6327f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_heartbeat_enable(cpu); 6337f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis return 0; 6347f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis} 6357f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6367f1baa063e2582dd52d83bb31508e9e84468c666Mike Travislate_initcall(uv_init_heartbeat); 6377f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 6387f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis#endif /* !CONFIG_HOTPLUG_CPU */ 6397f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis 640841582ea9e29a8f757c30c5377ce649586ba793aMike Travis/* Direct Legacy VGA I/O traffic to designated IOH */ 641841582ea9e29a8f757c30c5377ce649586ba793aMike Travisint uv_set_vga_state(struct pci_dev *pdev, bool decode, 6427ad35cf288fd63a19bf50e490440a992de808b2bDave Airlie unsigned int command_bits, u32 flags) 643841582ea9e29a8f757c30c5377ce649586ba793aMike Travis{ 644841582ea9e29a8f757c30c5377ce649586ba793aMike Travis int domain, bus, rc; 645841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 6467ad35cf288fd63a19bf50e490440a992de808b2bDave Airlie PR_DEVEL("devfn %x decode %d cmd %x flags %d\n", 6477ad35cf288fd63a19bf50e490440a992de808b2bDave Airlie pdev->devfn, decode, command_bits, flags); 648841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 6497ad35cf288fd63a19bf50e490440a992de808b2bDave Airlie if (!(flags & PCI_VGA_STATE_CHANGE_BRIDGE)) 650841582ea9e29a8f757c30c5377ce649586ba793aMike Travis return 0; 651841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 652841582ea9e29a8f757c30c5377ce649586ba793aMike Travis if ((command_bits & PCI_COMMAND_IO) == 0) 653841582ea9e29a8f757c30c5377ce649586ba793aMike Travis return 0; 654841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 655841582ea9e29a8f757c30c5377ce649586ba793aMike Travis domain = pci_domain_nr(pdev->bus); 656841582ea9e29a8f757c30c5377ce649586ba793aMike Travis bus = pdev->bus->number; 657841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 658841582ea9e29a8f757c30c5377ce649586ba793aMike Travis rc = uv_bios_set_legacy_vga_target(decode, domain, bus); 659841582ea9e29a8f757c30c5377ce649586ba793aMike Travis PR_DEVEL("vga decode %d %x:%x, rc: %d\n", decode, domain, bus, rc); 660841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 661841582ea9e29a8f757c30c5377ce649586ba793aMike Travis return rc; 662841582ea9e29a8f757c30c5377ce649586ba793aMike Travis} 663841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 6647f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis/* 6658da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner * Called on each cpu to initialize the per_cpu UV data area. 6660b1da1c8fc1a0cb71f17701efad06855a059f752Ingo Molnar * FIXME: hotplug not supported yet 6678da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner */ 6688da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steinervoid __cpuinit uv_cpu_init(void) 6698da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner{ 6708da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner /* CPU 0 initilization will be done via uv_system_init. */ 6718da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner if (!uv_blade_info) 6728da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner return; 6738da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner 6748da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner uv_blade_info[uv_numa_blade_id()].nr_online_cpus++; 6758da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner 6768da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner if (get_uv_system_type() == UV_NON_UNIQUE_APIC) 6778da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner set_x2apic_extra_bits(uv_hub_info->pnode); 6788da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner} 6798da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner 68078c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson/* 68178c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson * When NMI is received, print a stack trace. 68278c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson */ 6839c48f1c629ecfa114850c03f875c6691003214deDon Zickusint uv_handle_nmi(unsigned int reason, struct pt_regs *regs) 68478c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson{ 6851d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner unsigned long real_uv_nmi; 6861d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner int bid; 6871d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 68878c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson /* 6891d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner * Each blade has an MMR that indicates when an NMI has been sent 6901d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner * to cpus on the blade. If an NMI is detected, atomically 6911d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner * clear the MMR and update a per-blade NMI count used to 6921d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner * cause each cpu on the blade to notice a new NMI. 6931d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner */ 6941d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner bid = uv_numa_blade_id(); 6951d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner real_uv_nmi = (uv_read_local_mmr(UVH_NMI_MMR) & UV_NMI_PENDING_MASK); 6961d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 6971d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner if (unlikely(real_uv_nmi)) { 6981d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner spin_lock(&uv_blade_info[bid].nmi_lock); 6991d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner real_uv_nmi = (uv_read_local_mmr(UVH_NMI_MMR) & UV_NMI_PENDING_MASK); 7001d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner if (real_uv_nmi) { 7011d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner uv_blade_info[bid].nmi_count++; 7021d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner uv_write_local_mmr(UVH_NMI_MMR_CLEAR, UV_NMI_PENDING_MASK); 7031d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner } 7041d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner spin_unlock(&uv_blade_info[bid].nmi_lock); 7051d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner } 7061d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 7071d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner if (likely(__get_cpu_var(cpu_last_nmi_count) == uv_blade_info[bid].nmi_count)) 7089c48f1c629ecfa114850c03f875c6691003214deDon Zickus return NMI_DONE; 7091d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 7101d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner __get_cpu_var(cpu_last_nmi_count) = uv_blade_info[bid].nmi_count; 7111d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 7121d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner /* 7131d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner * Use a lock so only one cpu prints at a time. 7141d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner * This prevents intermixed output. 71578c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson */ 71678c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson spin_lock(&uv_nmi_lock); 7171d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner pr_info("UV NMI stack dump cpu %u:\n", smp_processor_id()); 71878c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson dump_stack(); 71978c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson spin_unlock(&uv_nmi_lock); 72078c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson 7219c48f1c629ecfa114850c03f875c6691003214deDon Zickus return NMI_HANDLED; 72278c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson} 72378c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson 72478c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Andersonvoid uv_register_nmi_notifier(void) 72578c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson{ 7269c48f1c629ecfa114850c03f875c6691003214deDon Zickus if (register_nmi_handler(NMI_UNKNOWN, uv_handle_nmi, 0, "uv")) 72778c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson printk(KERN_WARNING "UV NMI handler failed to register\n"); 72878c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson} 72978c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson 73078c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Andersonvoid uv_nmi_init(void) 73178c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson{ 73278c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson unsigned int value; 73378c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson 73478c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson /* 73578c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson * Unmask NMI on all cpus 73678c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson */ 73778c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson value = apic_read(APIC_LVT1) | APIC_DM_NMI; 73878c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson value &= ~APIC_LVT_MASKED; 73978c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson apic_write(APIC_LVT1, value); 74078c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson} 741c4bd1fdab0deec0f69aeabab22075cb22ac8ad44Marcin Slusarz 742c4bd1fdab0deec0f69aeabab22075cb22ac8ad44Marcin Slusarzvoid __init uv_system_init(void) 743ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner{ 74462b0cfc240b1d4601333912ef8760e0ca9ec2cecJack Steiner union uvh_rh_gam_config_mmr_u m_n_config; 745d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner union uvh_rh_gam_mmioh_overlay_config_mmr_u mmioh; 7469f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner union uvh_node_id_u node_id; 7479f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner unsigned long gnode_upper, lowmem_redir_base, lowmem_redir_size; 748d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner int bytes, nid, cpu, lcpu, pnode, blade, i, j, m_val, n_val, n_io; 749c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner int gnode_extra, max_pnode = 0; 7506a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner unsigned long mmr_base, present, paddr; 751d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner unsigned short pnode_mask, pnode_io_mask; 752ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 7532a919596c16b4333af851ff473ebf96e289ab90cJack Steiner printk(KERN_INFO "UV: Found %s hub\n", is_uv1_hub() ? "UV1" : "UV2"); 754918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner map_low_mmrs(); 755918bc960dc630b1a79c0d2991a81985812ff69f5Jack Steiner 75662b0cfc240b1d4601333912ef8760e0ca9ec2cecJack Steiner m_n_config.v = uv_read_local_mmr(UVH_RH_GAM_CONFIG_MMR ); 7579f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner m_val = m_n_config.s.m_skt; 7589f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner n_val = m_n_config.s.n_skt; 759d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner mmioh.v = uv_read_local_mmr(UVH_RH_GAM_MMIOH_OVERLAY_CONFIG_MMR); 7602a919596c16b4333af851ff473ebf96e289ab90cJack Steiner n_io = is_uv1_hub() ? mmioh.s1.n_io : mmioh.s2.n_io; 761ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner mmr_base = 762ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_read_local_mmr(UVH_RH_GAM_MMR_OVERLAY_CONFIG_MMR) & 763ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner ~UV_MMR_ENABLE; 764c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner pnode_mask = (1 << n_val) - 1; 765d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner pnode_io_mask = (1 << n_io) - 1; 766d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner 767c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner node_id.v = uv_read_local_mmr(UVH_NODE_ID); 768c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner gnode_extra = (node_id.s.node_id & ~((1 << n_val) - 1)) >> 1; 769c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner gnode_upper = ((unsigned long)gnode_extra << m_val); 770d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner printk(KERN_INFO "UV: N %d, M %d, N_IO: %d, gnode_upper 0x%lx, gnode_extra 0x%x, pnode_mask 0x%x, pnode_io_mask 0x%x\n", 771d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner n_val, m_val, n_io, gnode_upper, gnode_extra, pnode_mask, pnode_io_mask); 772c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner 773ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner printk(KERN_DEBUG "UV: global MMR base 0x%lx\n", mmr_base); 774ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 7759f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner for(i = 0; i < UVH_NODE_PRESENT_TABLE_DEPTH; i++) 7769f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_possible_blades += 7779f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner hweight64(uv_read_local_mmr( UVH_NODE_PRESENT_TABLE + i * 8)); 778da517a08ac5913cd80ce3507cddd00f2a091b13cJack Steiner 779da517a08ac5913cd80ce3507cddd00f2a091b13cJack Steiner /* uv_num_possible_blades() is really the hub count */ 780da517a08ac5913cd80ce3507cddd00f2a091b13cJack Steiner printk(KERN_INFO "UV: Found %d blades, %d hubs\n", 781da517a08ac5913cd80ce3507cddd00f2a091b13cJack Steiner is_uv1_hub() ? uv_num_possible_blades() : 782da517a08ac5913cd80ce3507cddd00f2a091b13cJack Steiner (uv_num_possible_blades() + 1) / 2, 783da517a08ac5913cd80ce3507cddd00f2a091b13cJack Steiner uv_num_possible_blades()); 784ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 785ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner bytes = sizeof(struct uv_blade_info) * uv_num_possible_blades(); 7861d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner uv_blade_info = kzalloc(bytes, GFP_KERNEL); 7879a8709d44139748fe2e0ab56d20d8c384c8b65adCyrill Gorcunov BUG_ON(!uv_blade_info); 7881d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner 7896c7184b77464261b7d55583a48accbd1350923a3Jack Steiner for (blade = 0; blade < uv_num_possible_blades(); blade++) 7906c7184b77464261b7d55583a48accbd1350923a3Jack Steiner uv_blade_info[blade].memory_nid = -1; 791ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 7929f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner get_lowmem_redirect(&lowmem_redir_base, &lowmem_redir_size); 7939f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 794ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner bytes = sizeof(uv_node_to_blade[0]) * num_possible_nodes(); 795ef020ab0109aa5cd6eac2e93519b7641c9862828Cliff Wickman uv_node_to_blade = kmalloc(bytes, GFP_KERNEL); 7969a8709d44139748fe2e0ab56d20d8c384c8b65adCyrill Gorcunov BUG_ON(!uv_node_to_blade); 797ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner memset(uv_node_to_blade, 255, bytes); 798ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 799ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner bytes = sizeof(uv_cpu_to_blade[0]) * num_possible_cpus(); 800ef020ab0109aa5cd6eac2e93519b7641c9862828Cliff Wickman uv_cpu_to_blade = kmalloc(bytes, GFP_KERNEL); 8019a8709d44139748fe2e0ab56d20d8c384c8b65adCyrill Gorcunov BUG_ON(!uv_cpu_to_blade); 802ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner memset(uv_cpu_to_blade, 255, bytes); 803ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 8049f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner blade = 0; 8059f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner for (i = 0; i < UVH_NODE_PRESENT_TABLE_DEPTH; i++) { 8069f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner present = uv_read_local_mmr(UVH_NODE_PRESENT_TABLE + i * 8); 8079f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner for (j = 0; j < 64; j++) { 8089f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner if (!test_bit(j, &present)) 8099f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner continue; 810d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner pnode = (i * 64 + j) & pnode_mask; 81136ac4b987bea9a95217e1af552252f275ca7fc44Jack Steiner uv_blade_info[blade].pnode = pnode; 8129f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_blade_info[blade].nr_possible_cpus = 0; 813ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_blade_info[blade].nr_online_cpus = 0; 8141d44e8288a0557c28c447d7e511f50d06ff93a34Jack Steiner spin_lock_init(&uv_blade_info[blade].nmi_lock); 81536ac4b987bea9a95217e1af552252f275ca7fc44Jack Steiner max_pnode = max(pnode, max_pnode); 8169f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner blade++; 817ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner } 8189f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner } 819ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 8207f5942329e0787087a5e4dced838cee711ac2b58Russ Anderson uv_bios_init(); 821b76365a18f7593c9df32a74bf2b4a39741b67bc6Russ Anderson uv_bios_get_sn_info(0, &uv_type, &sn_partition_id, &sn_coherency_id, 822b76365a18f7593c9df32a74bf2b4a39741b67bc6Russ Anderson &sn_region_size, &system_serial_number); 8237019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson uv_rtc_init(); 8247019cc2dd6fafcdc6b104005482dc910dcdbb797Russ Anderson 8259f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner for_each_present_cpu(cpu) { 82639d30770992895d55789de64bad2349510af68d0Mike Travis int apicid = per_cpu(x86_cpu_to_apicid, cpu); 82739d30770992895d55789de64bad2349510af68d0Mike Travis 8289f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner nid = cpu_to_node(cpu); 829c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson /* 830c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson * apic_pnode_shift must be set before calling uv_apicid_to_pnode(); 831c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson */ 832d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner uv_cpu_hub_info(cpu)->pnode_mask = pnode_mask; 833c8f730b1ab825f06733e1c074264f0078721f365Russ Anderson uv_cpu_hub_info(cpu)->apic_pnode_shift = uvh_apicid.s.pnode_shift; 8342a919596c16b4333af851ff473ebf96e289ab90cJack Steiner uv_cpu_hub_info(cpu)->hub_revision = uv_hub_info->hub_revision; 8352a919596c16b4333af851ff473ebf96e289ab90cJack Steiner 8366a469e4665bc158599de55d64388861d0a9f10f4Jack Steiner uv_cpu_hub_info(cpu)->m_shift = 64 - m_val; 8376a469e4665bc158599de55d64388861d0a9f10f4Jack Steiner uv_cpu_hub_info(cpu)->n_lshift = is_uv2_1_hub() ? 8386a469e4665bc158599de55d64388861d0a9f10f4Jack Steiner (m_val == 40 ? 40 : 39) : m_val; 8396a469e4665bc158599de55d64388861d0a9f10f4Jack Steiner 84039d30770992895d55789de64bad2349510af68d0Mike Travis pnode = uv_apicid_to_pnode(apicid); 8419f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner blade = boot_pnode_to_blade(pnode); 8429f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner lcpu = uv_blade_info[blade].nr_possible_cpus; 8439f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_blade_info[blade].nr_possible_cpus++; 8449f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner 8456c7184b77464261b7d55583a48accbd1350923a3Jack Steiner /* Any node on the blade, else will contain -1. */ 8466c7184b77464261b7d55583a48accbd1350923a3Jack Steiner uv_blade_info[blade].memory_nid = nid; 8476c7184b77464261b7d55583a48accbd1350923a3Jack Steiner 8489f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_cpu_hub_info(cpu)->lowmem_remap_base = lowmem_redir_base; 849189f67c4408806563a1f061f5c8bf184a6658477Jack Steiner uv_cpu_hub_info(cpu)->lowmem_remap_top = lowmem_redir_size; 8509f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_cpu_hub_info(cpu)->m_val = m_val; 851036ed8ba61b72c19dc5759446d4fe0844aa88255Robin Holt uv_cpu_hub_info(cpu)->n_val = n_val; 852ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_cpu_hub_info(cpu)->numa_blade_id = blade; 853ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_cpu_hub_info(cpu)->blade_processor_id = lcpu; 8549f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_cpu_hub_info(cpu)->pnode = pnode; 855036ed8ba61b72c19dc5759446d4fe0844aa88255Robin Holt uv_cpu_hub_info(cpu)->gpa_mask = (1UL << (m_val + n_val)) - 1; 8569f5314fb4d556d3132c784d0df47352b2830ca53Jack Steiner uv_cpu_hub_info(cpu)->gnode_upper = gnode_upper; 857c4ed3f04ba9defe22aa729d1646f970f791c03d7Jack Steiner uv_cpu_hub_info(cpu)->gnode_extra = gnode_extra; 858ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_cpu_hub_info(cpu)->global_mmr_base = mmr_base; 859b0f209898f1a177bd503d49215b8c6628797a81cRuss Anderson uv_cpu_hub_info(cpu)->coherency_domain_number = sn_coherency_id; 86039d30770992895d55789de64bad2349510af68d0Mike Travis uv_cpu_hub_info(cpu)->scir.offset = uv_scir_offset(apicid); 861ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_node_to_blade[nid] = blade; 862ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner uv_cpu_to_blade[cpu] = blade; 863ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner } 86483f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner 8656a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner /* Add blade/pnode info for nodes without cpus */ 8666a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner for_each_online_node(nid) { 8676a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner if (uv_node_to_blade[nid] >= 0) 8686a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner continue; 8696a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner paddr = node_start_pfn(nid) << PAGE_SHIFT; 8706a469e4665bc158599de55d64388861d0a9f10f4Jack Steiner pnode = uv_gpa_to_pnode(uv_soc_phys_ram_to_gpa(paddr)); 8716a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner blade = boot_pnode_to_blade(pnode); 8726a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner uv_node_to_blade[nid] = blade; 8736a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner } 8746a891a24e4d0056c365a90ff2d71c38fd366b0d0Jack Steiner 87583f5d894ca5280bfcd904dfeb1347c2da2b19aacJack Steiner map_gru_high(max_pnode); 876daf7b9c9216e2b82e4c14b7248a85286dab021c3Jack Steiner map_mmr_high(max_pnode); 877d8850ba425d9823d3184bd52f065899dac4689f9Jack Steiner map_mmioh_high(max_pnode & pnode_io_mask); 878ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner 8798da077d6f31da291ee3a7dd559671cb8ca48cbe2Jack Steiner uv_cpu_init(); 8807f1baa063e2582dd52d83bb31508e9e84468c666Mike Travis uv_scir_register_cpu_notifier(); 88178c06176466cbd1b3f0f67709d3023c40dbebcbdRuss Anderson uv_register_nmi_notifier(); 882a3d732f93785da17e0137210deadb4616f5536fcCliff Wickman proc_mkdir("sgi_uv", NULL); 883841582ea9e29a8f757c30c5377ce649586ba793aMike Travis 884841582ea9e29a8f757c30c5377ce649586ba793aMike Travis /* register Legacy VGA I/O redirection handler */ 885841582ea9e29a8f757c30c5377ce649586ba793aMike Travis pci_register_set_vga_state(uv_set_vga_state); 886818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman 887818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman /* 888818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman * For a kdump kernel the reset must be BOOT_ACPI, not BOOT_EFI, as 889818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman * EFI is not enabled in the kdump kernel. 890818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman */ 891818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman if (is_kdump_kernel()) 892818987e9a19c52240ba9b1c20f28f047eef76072Cliff Wickman reboot_type = BOOT_ACPI; 893ac23d4ee3f84de33c16ed7e68f9adee2386e74fbJack Steiner} 894107e0e0cd85beeee05af7ea374fda14d037ee500Suresh Siddha 895107e0e0cd85beeee05af7ea374fda14d037ee500Suresh Siddhaapic_driver(apic_x2apic_uv_x); 896