diff options
| -rw-r--r-- | arch/x86/include/asm/uv/uv_hub.h | 21 | ||||
| -rw-r--r-- | arch/x86/kernel/alternative.c | 2 | ||||
| -rw-r--r-- | arch/x86/kernel/apic/x2apic_uv_x.c | 24 | ||||
| -rw-r--r-- | arch/x86/kernel/irq_32.c | 9 | ||||
| -rw-r--r-- | arch/x86/mm/numa_64.c | 7 |
5 files changed, 50 insertions, 13 deletions
diff --git a/arch/x86/include/asm/uv/uv_hub.h b/arch/x86/include/asm/uv/uv_hub.h index bf6b88ef8eeb..e969f691cbfd 100644 --- a/arch/x86/include/asm/uv/uv_hub.h +++ b/arch/x86/include/asm/uv/uv_hub.h | |||
| @@ -5,7 +5,7 @@ | |||
| 5 | * | 5 | * |
| 6 | * SGI UV architectural definitions | 6 | * SGI UV architectural definitions |
| 7 | * | 7 | * |
| 8 | * Copyright (C) 2007-2008 Silicon Graphics, Inc. All rights reserved. | 8 | * Copyright (C) 2007-2010 Silicon Graphics, Inc. All rights reserved. |
| 9 | */ | 9 | */ |
| 10 | 10 | ||
| 11 | #ifndef _ASM_X86_UV_UV_HUB_H | 11 | #ifndef _ASM_X86_UV_UV_HUB_H |
| @@ -77,7 +77,8 @@ | |||
| 77 | * | 77 | * |
| 78 | * 1111110000000000 | 78 | * 1111110000000000 |
| 79 | * 5432109876543210 | 79 | * 5432109876543210 |
| 80 | * pppppppppplc0cch | 80 | * pppppppppplc0cch Nehalem-EX |
| 81 | * ppppppppplcc0cch Westmere-EX | ||
| 81 | * sssssssssss | 82 | * sssssssssss |
| 82 | * | 83 | * |
| 83 | * p = pnode bits | 84 | * p = pnode bits |
| @@ -148,12 +149,25 @@ struct uv_hub_info_s { | |||
| 148 | unsigned char m_val; | 149 | unsigned char m_val; |
| 149 | unsigned char n_val; | 150 | unsigned char n_val; |
| 150 | struct uv_scir_s scir; | 151 | struct uv_scir_s scir; |
| 152 | unsigned char apic_pnode_shift; | ||
| 151 | }; | 153 | }; |
| 152 | 154 | ||
| 153 | DECLARE_PER_CPU(struct uv_hub_info_s, __uv_hub_info); | 155 | DECLARE_PER_CPU(struct uv_hub_info_s, __uv_hub_info); |
| 154 | #define uv_hub_info (&__get_cpu_var(__uv_hub_info)) | 156 | #define uv_hub_info (&__get_cpu_var(__uv_hub_info)) |
| 155 | #define uv_cpu_hub_info(cpu) (&per_cpu(__uv_hub_info, cpu)) | 157 | #define uv_cpu_hub_info(cpu) (&per_cpu(__uv_hub_info, cpu)) |
| 156 | 158 | ||
| 159 | union uvh_apicid { | ||
| 160 | unsigned long v; | ||
| 161 | struct uvh_apicid_s { | ||
| 162 | unsigned long local_apic_mask : 24; | ||
| 163 | unsigned long local_apic_shift : 5; | ||
| 164 | unsigned long unused1 : 3; | ||
| 165 | unsigned long pnode_mask : 24; | ||
| 166 | unsigned long pnode_shift : 5; | ||
| 167 | unsigned long unused2 : 3; | ||
| 168 | } s; | ||
| 169 | }; | ||
| 170 | |||
| 157 | /* | 171 | /* |
| 158 | * Local & Global MMR space macros. | 172 | * Local & Global MMR space macros. |
| 159 | * Note: macros are intended to be used ONLY by inline functions | 173 | * Note: macros are intended to be used ONLY by inline functions |
| @@ -182,6 +196,7 @@ DECLARE_PER_CPU(struct uv_hub_info_s, __uv_hub_info); | |||
| 182 | #define UV_GLOBAL_MMR64_PNODE_BITS(p) \ | 196 | #define UV_GLOBAL_MMR64_PNODE_BITS(p) \ |
| 183 | (((unsigned long)(p)) << UV_GLOBAL_MMR64_PNODE_SHIFT) | 197 | (((unsigned long)(p)) << UV_GLOBAL_MMR64_PNODE_SHIFT) |
| 184 | 198 | ||
| 199 | #define UVH_APICID 0x002D0E00L | ||
| 185 | #define UV_APIC_PNODE_SHIFT 6 | 200 | #define UV_APIC_PNODE_SHIFT 6 |
| 186 | 201 | ||
| 187 | /* Local Bus from cpu's perspective */ | 202 | /* Local Bus from cpu's perspective */ |
| @@ -280,7 +295,7 @@ static inline void *uv_pnode_offset_to_vaddr(int pnode, unsigned long offset) | |||
| 280 | */ | 295 | */ |
| 281 | static inline int uv_apicid_to_pnode(int apicid) | 296 | static inline int uv_apicid_to_pnode(int apicid) |
| 282 | { | 297 | { |
| 283 | return (apicid >> UV_APIC_PNODE_SHIFT); | 298 | return (apicid >> uv_hub_info->apic_pnode_shift); |
| 284 | } | 299 | } |
| 285 | 300 | ||
| 286 | /* | 301 | /* |
diff --git a/arch/x86/kernel/alternative.c b/arch/x86/kernel/alternative.c index a36bb90aef53..5ceeca382820 100644 --- a/arch/x86/kernel/alternative.c +++ b/arch/x86/kernel/alternative.c | |||
| @@ -638,7 +638,7 @@ void *__kprobes text_poke_smp(void *addr, const void *opcode, size_t len) | |||
| 638 | atomic_set(&stop_machine_first, 1); | 638 | atomic_set(&stop_machine_first, 1); |
| 639 | wrote_text = 0; | 639 | wrote_text = 0; |
| 640 | /* Use __stop_machine() because the caller already got online_cpus. */ | 640 | /* Use __stop_machine() because the caller already got online_cpus. */ |
| 641 | __stop_machine(stop_machine_text_poke, (void *)&tpp, NULL); | 641 | __stop_machine(stop_machine_text_poke, (void *)&tpp, cpu_online_mask); |
| 642 | return addr; | 642 | return addr; |
| 643 | } | 643 | } |
| 644 | 644 | ||
diff --git a/arch/x86/kernel/apic/x2apic_uv_x.c b/arch/x86/kernel/apic/x2apic_uv_x.c index f744f54cb248..ed4118de249e 100644 --- a/arch/x86/kernel/apic/x2apic_uv_x.c +++ b/arch/x86/kernel/apic/x2apic_uv_x.c | |||
| @@ -5,7 +5,7 @@ | |||
| 5 | * | 5 | * |
| 6 | * SGI UV APIC functions (note: not an Intel compatible APIC) | 6 | * SGI UV APIC functions (note: not an Intel compatible APIC) |
| 7 | * | 7 | * |
| 8 | * Copyright (C) 2007-2009 Silicon Graphics, Inc. All rights reserved. | 8 | * Copyright (C) 2007-2010 Silicon Graphics, Inc. All rights reserved. |
| 9 | */ | 9 | */ |
| 10 | #include <linux/cpumask.h> | 10 | #include <linux/cpumask.h> |
| 11 | #include <linux/hardirq.h> | 11 | #include <linux/hardirq.h> |
| @@ -41,6 +41,7 @@ DEFINE_PER_CPU(int, x2apic_extra_bits); | |||
| 41 | 41 | ||
| 42 | static enum uv_system_type uv_system_type; | 42 | static enum uv_system_type uv_system_type; |
| 43 | static u64 gru_start_paddr, gru_end_paddr; | 43 | static u64 gru_start_paddr, gru_end_paddr; |
| 44 | static union uvh_apicid uvh_apicid; | ||
| 44 | int uv_min_hub_revision_id; | 45 | int uv_min_hub_revision_id; |
| 45 | EXPORT_SYMBOL_GPL(uv_min_hub_revision_id); | 46 | EXPORT_SYMBOL_GPL(uv_min_hub_revision_id); |
| 46 | static DEFINE_SPINLOCK(uv_nmi_lock); | 47 | static DEFINE_SPINLOCK(uv_nmi_lock); |
| @@ -70,12 +71,27 @@ static int early_get_nodeid(void) | |||
| 70 | return node_id.s.node_id; | 71 | return node_id.s.node_id; |
| 71 | } | 72 | } |
| 72 | 73 | ||
| 74 | static void __init early_get_apic_pnode_shift(void) | ||
| 75 | { | ||
| 76 | unsigned long *mmr; | ||
| 77 | |||
| 78 | mmr = early_ioremap(UV_LOCAL_MMR_BASE | UVH_APICID, sizeof(*mmr)); | ||
| 79 | uvh_apicid.v = *mmr; | ||
| 80 | early_iounmap(mmr, sizeof(*mmr)); | ||
| 81 | if (!uvh_apicid.v) | ||
| 82 | /* | ||
| 83 | * Old bios, use default value | ||
| 84 | */ | ||
| 85 | uvh_apicid.s.pnode_shift = UV_APIC_PNODE_SHIFT; | ||
| 86 | } | ||
| 87 | |||
| 73 | static int __init uv_acpi_madt_oem_check(char *oem_id, char *oem_table_id) | 88 | static int __init uv_acpi_madt_oem_check(char *oem_id, char *oem_table_id) |
| 74 | { | 89 | { |
| 75 | int nodeid; | 90 | int nodeid; |
| 76 | 91 | ||
| 77 | if (!strcmp(oem_id, "SGI")) { | 92 | if (!strcmp(oem_id, "SGI")) { |
| 78 | nodeid = early_get_nodeid(); | 93 | nodeid = early_get_nodeid(); |
| 94 | early_get_apic_pnode_shift(); | ||
| 79 | x86_platform.is_untracked_pat_range = uv_is_untracked_pat_range; | 95 | x86_platform.is_untracked_pat_range = uv_is_untracked_pat_range; |
| 80 | x86_platform.nmi_init = uv_nmi_init; | 96 | x86_platform.nmi_init = uv_nmi_init; |
| 81 | if (!strcmp(oem_table_id, "UVL")) | 97 | if (!strcmp(oem_table_id, "UVL")) |
| @@ -84,7 +100,7 @@ static int __init uv_acpi_madt_oem_check(char *oem_id, char *oem_table_id) | |||
| 84 | uv_system_type = UV_X2APIC; | 100 | uv_system_type = UV_X2APIC; |
| 85 | else if (!strcmp(oem_table_id, "UVH")) { | 101 | else if (!strcmp(oem_table_id, "UVH")) { |
| 86 | __get_cpu_var(x2apic_extra_bits) = | 102 | __get_cpu_var(x2apic_extra_bits) = |
| 87 | nodeid << (UV_APIC_PNODE_SHIFT - 1); | 103 | nodeid << (uvh_apicid.s.pnode_shift - 1); |
| 88 | uv_system_type = UV_NON_UNIQUE_APIC; | 104 | uv_system_type = UV_NON_UNIQUE_APIC; |
| 89 | return 1; | 105 | return 1; |
| 90 | } | 106 | } |
| @@ -716,6 +732,10 @@ void __init uv_system_init(void) | |||
| 716 | int apicid = per_cpu(x86_cpu_to_apicid, cpu); | 732 | int apicid = per_cpu(x86_cpu_to_apicid, cpu); |
| 717 | 733 | ||
| 718 | nid = cpu_to_node(cpu); | 734 | nid = cpu_to_node(cpu); |
| 735 | /* | ||
| 736 | * apic_pnode_shift must be set before calling uv_apicid_to_pnode(); | ||
| 737 | */ | ||
| 738 | uv_cpu_hub_info(cpu)->apic_pnode_shift = uvh_apicid.s.pnode_shift; | ||
| 719 | pnode = uv_apicid_to_pnode(apicid); | 739 | pnode = uv_apicid_to_pnode(apicid); |
| 720 | blade = boot_pnode_to_blade(pnode); | 740 | blade = boot_pnode_to_blade(pnode); |
| 721 | lcpu = uv_blade_info[blade].nr_possible_cpus; | 741 | lcpu = uv_blade_info[blade].nr_possible_cpus; |
diff --git a/arch/x86/kernel/irq_32.c b/arch/x86/kernel/irq_32.c index 64668dbf00a4..96656f207751 100644 --- a/arch/x86/kernel/irq_32.c +++ b/arch/x86/kernel/irq_32.c | |||
| @@ -17,6 +17,7 @@ | |||
| 17 | #include <linux/delay.h> | 17 | #include <linux/delay.h> |
| 18 | #include <linux/uaccess.h> | 18 | #include <linux/uaccess.h> |
| 19 | #include <linux/percpu.h> | 19 | #include <linux/percpu.h> |
| 20 | #include <linux/mm.h> | ||
| 20 | 21 | ||
| 21 | #include <asm/apic.h> | 22 | #include <asm/apic.h> |
| 22 | 23 | ||
| @@ -125,7 +126,9 @@ void __cpuinit irq_ctx_init(int cpu) | |||
| 125 | if (per_cpu(hardirq_ctx, cpu)) | 126 | if (per_cpu(hardirq_ctx, cpu)) |
| 126 | return; | 127 | return; |
| 127 | 128 | ||
| 128 | irqctx = (union irq_ctx *)__get_free_pages(THREAD_FLAGS, THREAD_ORDER); | 129 | irqctx = page_address(alloc_pages_node(cpu_to_node(cpu), |
| 130 | THREAD_FLAGS, | ||
| 131 | THREAD_ORDER)); | ||
| 129 | irqctx->tinfo.task = NULL; | 132 | irqctx->tinfo.task = NULL; |
| 130 | irqctx->tinfo.exec_domain = NULL; | 133 | irqctx->tinfo.exec_domain = NULL; |
| 131 | irqctx->tinfo.cpu = cpu; | 134 | irqctx->tinfo.cpu = cpu; |
| @@ -134,7 +137,9 @@ void __cpuinit irq_ctx_init(int cpu) | |||
| 134 | 137 | ||
| 135 | per_cpu(hardirq_ctx, cpu) = irqctx; | 138 | per_cpu(hardirq_ctx, cpu) = irqctx; |
| 136 | 139 | ||
| 137 | irqctx = (union irq_ctx *)__get_free_pages(THREAD_FLAGS, THREAD_ORDER); | 140 | irqctx = page_address(alloc_pages_node(cpu_to_node(cpu), |
| 141 | THREAD_FLAGS, | ||
| 142 | THREAD_ORDER)); | ||
| 138 | irqctx->tinfo.task = NULL; | 143 | irqctx->tinfo.task = NULL; |
| 139 | irqctx->tinfo.exec_domain = NULL; | 144 | irqctx->tinfo.exec_domain = NULL; |
| 140 | irqctx->tinfo.cpu = cpu; | 145 | irqctx->tinfo.cpu = cpu; |
diff --git a/arch/x86/mm/numa_64.c b/arch/x86/mm/numa_64.c index 60f498511dd6..7ffc9b727efd 100644 --- a/arch/x86/mm/numa_64.c +++ b/arch/x86/mm/numa_64.c | |||
| @@ -178,11 +178,8 @@ static void * __init early_node_mem(int nodeid, unsigned long start, | |||
| 178 | 178 | ||
| 179 | /* extend the search scope */ | 179 | /* extend the search scope */ |
| 180 | end = max_pfn_mapped << PAGE_SHIFT; | 180 | end = max_pfn_mapped << PAGE_SHIFT; |
| 181 | if (end > (MAX_DMA32_PFN<<PAGE_SHIFT)) | 181 | start = MAX_DMA_PFN << PAGE_SHIFT; |
| 182 | start = MAX_DMA32_PFN<<PAGE_SHIFT; | 182 | mem = memblock_find_in_range(start, end, size, align); |
| 183 | else | ||
| 184 | start = MAX_DMA_PFN<<PAGE_SHIFT; | ||
| 185 | mem = memblock_x86_find_in_range_node(nodeid, start, end, size, align); | ||
| 186 | if (mem != MEMBLOCK_ERROR) | 183 | if (mem != MEMBLOCK_ERROR) |
| 187 | return __va(mem); | 184 | return __va(mem); |
| 188 | 185 | ||
