aboutsummaryrefslogtreecommitdiff
path: root/arch/x86/kernel/cpu/common.c
diff options
context:
space:
mode:
authorYinghai Lu <Yinghai.Lu@Sun.COM>2008-01-30 13:33:32 +0100
committerIngo Molnar <mingo@elte.hu>2008-01-30 13:33:32 +0100
commit093af8d7f0ba3c6be1485973508584ef081e9f93 (patch)
tree0a2db2401e09764e654efafbea60f6d5d6894dcd /arch/x86/kernel/cpu/common.c
parent11201e603d28a1cb7a4bb1d65f39e61629c97a28 (diff)
x86_32: trim memory by updating e820
when MTRRs are not covering the whole e820 table, we need to trim the RAM and need to update e820. reuse some code on 64-bit as well. here need to add early_get_cap and use it in early_cpu_detect, and move mtrr_bp_init early. The code successfully trimmed the memory map on Justin's system: from: [ 0.000000] BIOS-e820: 0000000100000000 - 000000022c000000 (usable) to: [ 0.000000] modified: 0000000100000000 - 0000000228000000 (usable) [ 0.000000] modified: 0000000228000000 - 000000022c000000 (reserved) According to Justin it makes quite a difference: | When I boot the box without any trimming it acts like a 286 or 386, | takes about 10 minutes to boot (using raptor disks). Signed-off-by: Yinghai Lu <yinghai.lu@sun.com> Tested-by: Justin Piszcz <jpiszcz@lucidpixels.com> Signed-off-by: Ingo Molnar <mingo@elte.hu> Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Diffstat (limited to 'arch/x86/kernel/cpu/common.c')
-rw-r--r--arch/x86/kernel/cpu/common.c30
1 files changed, 29 insertions, 1 deletions
diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c
index 56cc341cc58..bba850b05d0 100644
--- a/arch/x86/kernel/cpu/common.c
+++ b/arch/x86/kernel/cpu/common.c
@@ -278,6 +278,33 @@ void __init cpu_detect(struct cpuinfo_x86 *c)
c->x86_cache_alignment = ((misc >> 8) & 0xff) * 8;
}
}
+static void __cpuinit early_get_cap(struct cpuinfo_x86 *c)
+{
+ u32 tfms, xlvl;
+ int ebx;
+
+ memset(&c->x86_capability, 0, sizeof c->x86_capability);
+ if (have_cpuid_p()) {
+ /* Intel-defined flags: level 0x00000001 */
+ if (c->cpuid_level >= 0x00000001) {
+ u32 capability, excap;
+ cpuid(0x00000001, &tfms, &ebx, &excap, &capability);
+ c->x86_capability[0] = capability;
+ c->x86_capability[4] = excap;
+ }
+
+ /* AMD-defined flags: level 0x80000001 */
+ xlvl = cpuid_eax(0x80000000);
+ if ((xlvl & 0xffff0000) == 0x80000000) {
+ if (xlvl >= 0x80000001) {
+ c->x86_capability[1] = cpuid_edx(0x80000001);
+ c->x86_capability[6] = cpuid_ecx(0x80000001);
+ }
+ }
+
+ }
+
+}
/* Do minimum CPU detection early.
Fields really needed: vendor, cpuid_level, family, model, mask, cache alignment.
@@ -306,6 +333,8 @@ static void __init early_cpu_detect(void)
early_init_intel(c);
break;
}
+
+ early_get_cap(c);
}
static void __cpuinit generic_identify(struct cpuinfo_x86 * c)
@@ -485,7 +514,6 @@ void __init identify_boot_cpu(void)
identify_cpu(&boot_cpu_data);
sysenter_setup();
enable_sep_cpu();
- mtrr_bp_init();
}
void __cpuinit identify_secondary_cpu(struct cpuinfo_x86 *c)