aboutsummaryrefslogtreecommitdiffstats
path: root/arch/i386/kernel/cpu/common.c
diff options
context:
space:
mode:
authorJeremy Fitzhardinge <jeremy@goop.org>2007-05-02 13:27:16 -0400
committerAndi Kleen <andi@basil.nowhere.org>2007-05-02 13:27:16 -0400
commit7c3576d261ce046789a7db14f43303f8120910c7 (patch)
treead27a8459bbcdb183fe2411aec3b840942992ad5 /arch/i386/kernel/cpu/common.c
parent7a61d35d4b4056e7711031202da7605e052f4137 (diff)
[PATCH] i386: Convert PDA into the percpu section
Currently x86 (similar to x84-64) has a special per-cpu structure called "i386_pda" which can be easily and efficiently referenced via the %fs register. An ELF section is more flexible than a structure, allowing any piece of code to use this area. Indeed, such a section already exists: the per-cpu area. So this patch: (1) Removes the PDA and uses per-cpu variables for each current member. (2) Replaces the __KERNEL_PDA segment with __KERNEL_PERCPU. (3) Creates a per-cpu mirror of __per_cpu_offset called this_cpu_off, which can be used to calculate addresses for this CPU's variables. (4) Simplifies startup, because %fs doesn't need to be loaded with a special segment at early boot; it can be deferred until the first percpu area is allocated (or never for UP). The result is less code and one less x86-specific concept. Signed-off-by: Rusty Russell <rusty@rustcorp.com.au> Signed-off-by: Jeremy Fitzhardinge <jeremy@xensource.com> Signed-off-by: Andi Kleen <ak@suse.de> Cc: Andi Kleen <ak@suse.de>
Diffstat (limited to 'arch/i386/kernel/cpu/common.c')
-rw-r--r--arch/i386/kernel/cpu/common.c17
1 files changed, 3 insertions, 14 deletions
diff --git a/arch/i386/kernel/cpu/common.c b/arch/i386/kernel/cpu/common.c
index 7a4c036d93c8..27e00565f5e4 100644
--- a/arch/i386/kernel/cpu/common.c
+++ b/arch/i386/kernel/cpu/common.c
@@ -18,7 +18,6 @@
18#include <asm/apic.h> 18#include <asm/apic.h>
19#include <mach_apic.h> 19#include <mach_apic.h>
20#endif 20#endif
21#include <asm/pda.h>
22 21
23#include "cpu.h" 22#include "cpu.h"
24 23
@@ -47,13 +46,10 @@ DEFINE_PER_CPU(struct gdt_page, gdt_page) = { .gdt = {
47 [GDT_ENTRY_APMBIOS_BASE+2] = { 0x0000ffff, 0x00409200 }, /* data */ 46 [GDT_ENTRY_APMBIOS_BASE+2] = { 0x0000ffff, 0x00409200 }, /* data */
48 47
49 [GDT_ENTRY_ESPFIX_SS] = { 0x00000000, 0x00c09200 }, 48 [GDT_ENTRY_ESPFIX_SS] = { 0x00000000, 0x00c09200 },
50 [GDT_ENTRY_PDA] = { 0x00000000, 0x00c09200 }, /* set in setup_pda */ 49 [GDT_ENTRY_PERCPU] = { 0x00000000, 0x00000000 },
51} }; 50} };
52EXPORT_PER_CPU_SYMBOL_GPL(gdt_page); 51EXPORT_PER_CPU_SYMBOL_GPL(gdt_page);
53 52
54DEFINE_PER_CPU(struct i386_pda, _cpu_pda);
55EXPORT_PER_CPU_SYMBOL(_cpu_pda);
56
57static int cachesize_override __cpuinitdata = -1; 53static int cachesize_override __cpuinitdata = -1;
58static int disable_x86_fxsr __cpuinitdata; 54static int disable_x86_fxsr __cpuinitdata;
59static int disable_x86_serial_nr __cpuinitdata = 1; 55static int disable_x86_serial_nr __cpuinitdata = 1;
@@ -634,21 +630,14 @@ void __init early_cpu_init(void)
634#endif 630#endif
635} 631}
636 632
637/* Make sure %gs is initialized properly in idle threads */ 633/* Make sure %fs is initialized properly in idle threads */
638struct pt_regs * __devinit idle_regs(struct pt_regs *regs) 634struct pt_regs * __devinit idle_regs(struct pt_regs *regs)
639{ 635{
640 memset(regs, 0, sizeof(struct pt_regs)); 636 memset(regs, 0, sizeof(struct pt_regs));
641 regs->xfs = __KERNEL_PDA; 637 regs->xfs = __KERNEL_PERCPU;
642 return regs; 638 return regs;
643} 639}
644 640
645/* Initial PDA used by boot CPU */
646struct i386_pda boot_pda = {
647 ._pda = &boot_pda,
648 .cpu_number = 0,
649 .pcurrent = &init_task,
650};
651
652/* 641/*
653 * cpu_init() initializes state that is per-CPU. Some data is already 642 * cpu_init() initializes state that is per-CPU. Some data is already
654 * initialized (naturally) in the bootstrap process, such as the GDT 643 * initialized (naturally) in the bootstrap process, such as the GDT