diff options
author | Ingo Molnar <mingo@elte.hu> | 2009-02-09 06:16:59 -0500 |
---|---|---|
committer | Ingo Molnar <mingo@elte.hu> | 2009-02-09 06:16:59 -0500 |
commit | eca217b36e5d7d4377493d5cedd89105e66a5a72 (patch) | |
tree | 71f0ecd5225c3033d509b77a23ad7bc576cf0ab6 /arch/x86/kernel/cpu/common.c | |
parent | 54a353a0f845c1dad5fc8183872e750d667838ac (diff) | |
parent | e4d0407185cdbdcfd99fc23bde2e5454bbc46329 (diff) |
Merge branch 'x86/paravirt' into x86/apic
Conflicts:
arch/x86/mach-voyager/voyager_smp.c
Diffstat (limited to 'arch/x86/kernel/cpu/common.c')
-rw-r--r-- | arch/x86/kernel/cpu/common.c | 25 |
1 files changed, 15 insertions, 10 deletions
diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c index c4bdc7f00207..cbcdb796d47f 100644 --- a/arch/x86/kernel/cpu/common.c +++ b/arch/x86/kernel/cpu/common.c | |||
@@ -296,23 +296,28 @@ static char __cpuinit *table_lookup_model(struct cpuinfo_x86 *c) | |||
296 | 296 | ||
297 | __u32 cleared_cpu_caps[NCAPINTS] __cpuinitdata; | 297 | __u32 cleared_cpu_caps[NCAPINTS] __cpuinitdata; |
298 | 298 | ||
299 | void load_percpu_segment(int cpu) | ||
300 | { | ||
301 | #ifdef CONFIG_X86_32 | ||
302 | loadsegment(fs, __KERNEL_PERCPU); | ||
303 | #else | ||
304 | loadsegment(gs, 0); | ||
305 | wrmsrl(MSR_GS_BASE, (unsigned long)per_cpu(irq_stack_union.gs_base, cpu)); | ||
306 | #endif | ||
307 | } | ||
308 | |||
299 | /* Current gdt points %fs at the "master" per-cpu area: after this, | 309 | /* Current gdt points %fs at the "master" per-cpu area: after this, |
300 | * it's on the real one. */ | 310 | * it's on the real one. */ |
301 | void switch_to_new_gdt(void) | 311 | void switch_to_new_gdt(int cpu) |
302 | { | 312 | { |
303 | struct desc_ptr gdt_descr; | 313 | struct desc_ptr gdt_descr; |
304 | int cpu = smp_processor_id(); | ||
305 | 314 | ||
306 | gdt_descr.address = (long)get_cpu_gdt_table(cpu); | 315 | gdt_descr.address = (long)get_cpu_gdt_table(cpu); |
307 | gdt_descr.size = GDT_SIZE - 1; | 316 | gdt_descr.size = GDT_SIZE - 1; |
308 | load_gdt(&gdt_descr); | 317 | load_gdt(&gdt_descr); |
309 | /* Reload the per-cpu base */ | 318 | /* Reload the per-cpu base */ |
310 | #ifdef CONFIG_X86_32 | 319 | |
311 | loadsegment(fs, __KERNEL_PERCPU); | 320 | load_percpu_segment(cpu); |
312 | #else | ||
313 | loadsegment(gs, 0); | ||
314 | wrmsrl(MSR_GS_BASE, (unsigned long)per_cpu(irq_stack_union.gs_base, cpu)); | ||
315 | #endif | ||
316 | } | 321 | } |
317 | 322 | ||
318 | static struct cpu_dev *cpu_devs[X86_VENDOR_NUM] = {}; | 323 | static struct cpu_dev *cpu_devs[X86_VENDOR_NUM] = {}; |
@@ -1029,7 +1034,7 @@ void __cpuinit cpu_init(void) | |||
1029 | * and set up the GDT descriptor: | 1034 | * and set up the GDT descriptor: |
1030 | */ | 1035 | */ |
1031 | 1036 | ||
1032 | switch_to_new_gdt(); | 1037 | switch_to_new_gdt(cpu); |
1033 | loadsegment(fs, 0); | 1038 | loadsegment(fs, 0); |
1034 | 1039 | ||
1035 | load_idt((const struct desc_ptr *)&idt_descr); | 1040 | load_idt((const struct desc_ptr *)&idt_descr); |
@@ -1131,7 +1136,7 @@ void __cpuinit cpu_init(void) | |||
1131 | clear_in_cr4(X86_CR4_VME|X86_CR4_PVI|X86_CR4_TSD|X86_CR4_DE); | 1136 | clear_in_cr4(X86_CR4_VME|X86_CR4_PVI|X86_CR4_TSD|X86_CR4_DE); |
1132 | 1137 | ||
1133 | load_idt(&idt_descr); | 1138 | load_idt(&idt_descr); |
1134 | switch_to_new_gdt(); | 1139 | switch_to_new_gdt(cpu); |
1135 | 1140 | ||
1136 | /* | 1141 | /* |
1137 | * Set up and load the per-CPU TSS and LDT | 1142 | * Set up and load the per-CPU TSS and LDT |