linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [X86] Remove unnecessary code in 64bit CPU identification.
@ 2008-05-20  4:09 Dave Jones
  2008-05-20  4:14 ` Dave Jones
  2008-05-20 14:46 ` H. Peter Anvin
  0 siblings, 2 replies; 10+ messages in thread
From: Dave Jones @ 2008-05-20  4:09 UTC (permalink / raw)
  To: Linux Kernel; +Cc: Ingo Molnar, Thomas Gleixner, hpa

There were no 64bit Transmeta CPUs made (and it'd be something of
a surprise if they started any time soon).   To the best of my knowledge,
no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
By removing this code, we can also eliminate calling cpuid 0x80000007 twice.

Signed-off-by: Dave Jones <davej@redhat.com>

diff --git a/arch/x86/kernel/setup_64.c b/arch/x86/kernel/setup_64.c
index ff62838..0380726 100644
--- a/arch/x86/kernel/setup_64.c
+++ b/arch/x86/kernel/setup_64.c
@@ -1042,20 +1042,11 @@ static void __cpuinit early_identify_cpu(struct cpuinfo_x86 *c)
 		}
 		if (xlvl >= 0x80000004)
 			get_model_name(c); /* Default name */
-	}
 
-	/* Transmeta-defined flags: level 0x80860001 */
-	xlvl = cpuid_eax(0x80860000);
-	if ((xlvl & 0xffff0000) == 0x80860000) {
-		/* Don't set x86_cpuid_level here for now to not confuse. */
-		if (xlvl >= 0x80860001)
-			c->x86_capability[2] = cpuid_edx(0x80860001);
+		if (xlvl >= 0x80000007)
+			c->x86_power = cpuid_edx(0x80000007);
 	}
 
-	c->extended_cpuid_level = cpuid_eax(0x80000000);
-	if (c->extended_cpuid_level >= 0x80000007)
-		c->x86_power = cpuid_edx(0x80000007);
-
 	switch (c->x86_vendor) {
 	case X86_VENDOR_AMD:
 		early_init_amd(c);



^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20  4:09 [X86] Remove unnecessary code in 64bit CPU identification Dave Jones
@ 2008-05-20  4:14 ` Dave Jones
  2008-05-20 14:46 ` H. Peter Anvin
  1 sibling, 0 replies; 10+ messages in thread
From: Dave Jones @ 2008-05-20  4:14 UTC (permalink / raw)
  To: Linux Kernel; +Cc: Ingo Molnar, Thomas Gleixner, hpa

On Tue, May 20, 2008 at 12:09:35AM -0400, Dave Jones wrote:
 > There were no 64bit Transmeta CPUs made (and it'd be something of
 > a surprise if they started any time soon).   To the best of my knowledge,
 > no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
 > By removing this code, we can also eliminate calling cpuid 0x80000007 twice.

argh, after reading this a dozen times, I send it, and then notice a typo.
That should be ' eliminate calling cpuid 0x80000000 twice'

	Dave

-- 
http://www.codemonkey.org.uk

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20  4:09 [X86] Remove unnecessary code in 64bit CPU identification Dave Jones
  2008-05-20  4:14 ` Dave Jones
@ 2008-05-20 14:46 ` H. Peter Anvin
  2008-05-20 15:16   ` Dave Jones
  1 sibling, 1 reply; 10+ messages in thread
From: H. Peter Anvin @ 2008-05-20 14:46 UTC (permalink / raw)
  To: Dave Jones; +Cc: Linux Kernel, Ingo Molnar, Thomas Gleixner

Dave Jones wrote:
> There were no 64bit Transmeta CPUs made (and it'd be something of
> a surprise if they started any time soon).   To the best of my knowledge,
> no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
> By removing this code, we can also eliminate calling cpuid 0x80000007 twice.
> 
> Signed-off-by: Dave Jones <davej@redhat.com>

I'd really like to avoid divergences between the 32-bit and 64-bit code 
if they can be avoided at this point.  These codes need to be unified, 
not further split.

	-hpa

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20 14:46 ` H. Peter Anvin
@ 2008-05-20 15:16   ` Dave Jones
  2008-05-20 17:58     ` H. Peter Anvin
  0 siblings, 1 reply; 10+ messages in thread
From: Dave Jones @ 2008-05-20 15:16 UTC (permalink / raw)
  To: H. Peter Anvin; +Cc: Linux Kernel, Ingo Molnar, Thomas Gleixner

On Tue, May 20, 2008 at 07:46:57AM -0700, H. Peter Anvin wrote:
 > Dave Jones wrote:
 > > There were no 64bit Transmeta CPUs made (and it'd be something of
 > > a surprise if they started any time soon).   To the best of my knowledge,
 > > no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
 > > By removing this code, we can also eliminate calling cpuid 0x80000007 twice.
 > > 
 > > Signed-off-by: Dave Jones <davej@redhat.com>
 > 
 > I'd really like to avoid divergences between the 32-bit and 64-bit code 
 > if they can be avoided at this point.  These codes need to be unified, 
 > not further split.

Umm, the 32 bit code has the per-vendor stuff removed from setup.c, and factored
out into per-vendor files in arch/x86/kernel/cpu/  Because the 64bit version
doesn't do that (yet), my removal of this code actually gets us closer to unification.
After my patch, neither of the setup.c files have the Transmeta bits :)

	Dave

-- 
http://www.codemonkey.org.uk

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20 15:16   ` Dave Jones
@ 2008-05-20 17:58     ` H. Peter Anvin
  2008-05-20 18:06       ` Dave Jones
  2008-05-20 19:18       ` Dave Jones
  0 siblings, 2 replies; 10+ messages in thread
From: H. Peter Anvin @ 2008-05-20 17:58 UTC (permalink / raw)
  To: Dave Jones, H. Peter Anvin, Linux Kernel, Ingo Molnar, Thomas Gleixner

Dave Jones wrote:
> On Tue, May 20, 2008 at 07:46:57AM -0700, H. Peter Anvin wrote:
>  > Dave Jones wrote:
>  > > There were no 64bit Transmeta CPUs made (and it'd be something of
>  > > a surprise if they started any time soon).   To the best of my knowledge,
>  > > no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
>  > > By removing this code, we can also eliminate calling cpuid 0x80000007 twice.
>  > > 
>  > > Signed-off-by: Dave Jones <davej@redhat.com>
>  > 
>  > I'd really like to avoid divergences between the 32-bit and 64-bit code 
>  > if they can be avoided at this point.  These codes need to be unified, 
>  > not further split.
> 
> Umm, the 32 bit code has the per-vendor stuff removed from setup.c, and factored
> out into per-vendor files in arch/x86/kernel/cpu/  Because the 64bit version
> doesn't do that (yet), my removal of this code actually gets us closer to unification.
> After my patch, neither of the setup.c files have the Transmeta bits :)
> 

*Shrug* ... it seems like pointless churn to code that really needs to 
die to me.

	-hpa

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20 17:58     ` H. Peter Anvin
@ 2008-05-20 18:06       ` Dave Jones
  2008-05-20 19:18       ` Dave Jones
  1 sibling, 0 replies; 10+ messages in thread
From: Dave Jones @ 2008-05-20 18:06 UTC (permalink / raw)
  To: H. Peter Anvin; +Cc: Linux Kernel, Ingo Molnar, Thomas Gleixner

On Tue, May 20, 2008 at 10:58:07AM -0700, H. Peter Anvin wrote:
 > Dave Jones wrote:
 > > On Tue, May 20, 2008 at 07:46:57AM -0700, H. Peter Anvin wrote:
 > >  > Dave Jones wrote:
 > >  > > There were no 64bit Transmeta CPUs made (and it'd be something of
 > >  > > a surprise if they started any time soon).   To the best of my knowledge,
 > >  > > no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
 > >  > > By removing this code, we can also eliminate calling cpuid 0x80000007 twice.
 > >  > > 
 > >  > > Signed-off-by: Dave Jones <davej@redhat.com>
 > >  > 
 > >  > I'd really like to avoid divergences between the 32-bit and 64-bit code 
 > >  > if they can be avoided at this point.  These codes need to be unified, 
 > >  > not further split.
 > > 
 > > Umm, the 32 bit code has the per-vendor stuff removed from setup.c, and factored
 > > out into per-vendor files in arch/x86/kernel/cpu/  Because the 64bit version
 > > doesn't do that (yet), my removal of this code actually gets us closer to unification.
 > > After my patch, neither of the setup.c files have the Transmeta bits :)
 > > 
 > 
 > *Shrug* ... it seems like pointless churn to code that really needs to 
 > die to me.

setup_64.c |   13 ++-----------
 1 file changed, 2 insertions(+), 11 deletions(-)

It's a slow death, but it's easier to chip away at the obvious parts..

	Dave

-- 
http://www.codemonkey.org.uk

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20 17:58     ` H. Peter Anvin
  2008-05-20 18:06       ` Dave Jones
@ 2008-05-20 19:18       ` Dave Jones
  2008-05-20 19:42         ` H. Peter Anvin
  2008-05-21 23:55         ` H. Peter Anvin
  1 sibling, 2 replies; 10+ messages in thread
From: Dave Jones @ 2008-05-20 19:18 UTC (permalink / raw)
  To: H. Peter Anvin; +Cc: Linux Kernel, Ingo Molnar, Thomas Gleixner

On Tue, May 20, 2008 at 10:58:07AM -0700, H. Peter Anvin wrote:
 > Dave Jones wrote:
 > > On Tue, May 20, 2008 at 07:46:57AM -0700, H. Peter Anvin wrote:
 > >  > Dave Jones wrote:
 > >  > > There were no 64bit Transmeta CPUs made (and it'd be something of
 > >  > > a surprise if they started any time soon).   To the best of my knowledge,
 > >  > > no CPU vendor cloned the 80860000 cpuid space claimed by Transmeta.
 > >  > > By removing this code, we can also eliminate calling cpuid 0x80000007 twice.
 > >  > > 
 > >  > > Signed-off-by: Dave Jones <davej@redhat.com>
 > >  > 
 > >  > I'd really like to avoid divergences between the 32-bit and 64-bit code 
 > >  > if they can be avoided at this point.  These codes need to be unified, 
 > >  > not further split.
 > > 
 > > Umm, the 32 bit code has the per-vendor stuff removed from setup.c, and factored
 > > out into per-vendor files in arch/x86/kernel/cpu/  Because the 64bit version
 > > doesn't do that (yet), my removal of this code actually gets us closer to unification.
 > > After my patch, neither of the setup.c files have the Transmeta bits :)
 > > 
 > 
 > *Shrug* ... it seems like pointless churn to code that really needs to 
 > die to me.

Moving along the same direction..  Moving the vendor specific bits out of setup_64.c
into cpu/ would go a long way towards killing of setup64.c.  I took a first pass at doing this
in the diff below. So far I only looked at the AMD specific bits, and haven't done
a complete conversion to cpu_dev style initialisation as done on 32bit, but that
can easily be performed later after moving all the code out into its respective places.
(downside: a bunch of externs in the interim).

comments on this before I go any further?

	Dave

diff --git a/arch/x86/kernel/cpu/Makefile b/arch/x86/kernel/cpu/Makefile
index a0c6f81..ef065c1 100644
--- a/arch/x86/kernel/cpu/Makefile
+++ b/arch/x86/kernel/cpu/Makefile
@@ -7,6 +7,7 @@ obj-y			+= proc.o feature_names.o
 
 obj-$(CONFIG_X86_32)	+= common.o bugs.o
 obj-$(CONFIG_X86_32)	+= amd.o
+obj-$(CONFIG_X86_64)	+= amd_64.o
 obj-$(CONFIG_X86_32)	+= cyrix.o
 obj-$(CONFIG_X86_32)	+= centaur.o
 obj-$(CONFIG_X86_32)	+= transmeta.o
diff --git a/arch/x86/kernel/cpu/amd_64.c b/arch/x86/kernel/cpu/amd_64.c
new file mode 100644
index 0000000..a0ba1eb
--- /dev/null
+++ b/arch/x86/kernel/cpu/amd_64.c
@@ -0,0 +1,252 @@
+#include <linux/init.h>
+#include <linux/bitops.h>
+#include <linux/mm.h>
+#include <asm/io.h>
+#include <asm/processor.h>
+#include <asm/apic.h>
+
+#include <asm/numa_64.h>
+#include <asm/mmconfig.h>
+#include <asm/cacheflush.h>
+
+#include <mach_apic.h>
+#include "cpu.h"
+
+extern int __cpuinit get_model_name(struct cpuinfo_x86 *c);
+extern void __cpuinit display_cacheinfo(struct cpuinfo_x86 *c);
+
+int force_mwait __cpuinitdata;
+
+#ifdef CONFIG_NUMA
+static int __cpuinit nearby_node(int apicid)
+{
+        int i, node;
+
+        for (i = apicid - 1; i >= 0; i--) {
+                node = apicid_to_node[i];
+                if (node != NUMA_NO_NODE && node_online(node))
+                        return node;
+        }
+        for (i = apicid + 1; i < MAX_LOCAL_APIC; i++) {
+                node = apicid_to_node[i];
+                if (node != NUMA_NO_NODE && node_online(node))
+                        return node;
+        }
+        return first_node(node_online_map); /* Shouldn't happen */
+}
+#endif
+
+static void __cpuinit early_init_amd_mc(struct cpuinfo_x86 *c)
+{
+#ifdef CONFIG_SMP
+	unsigned bits, ecx;
+
+	/* Multi core CPU? */
+	if (c->extended_cpuid_level < 0x80000008)
+		return;
+
+	ecx = cpuid_ecx(0x80000008);
+
+	c->x86_max_cores = (ecx & 0xff) + 1;
+
+	/* CPU telling us the core id bits shift? */
+	bits = (ecx >> 12) & 0xF;
+
+	/* Otherwise recompute */
+	if (bits == 0) {
+	        while ((1 << bits) < c->x86_max_cores)
+	                bits++;
+	}
+
+	c->x86_coreid_bits = bits;
+#endif
+}
+
+#define ENABLE_C1E_MASK         0x18000000
+#define CPUID_PROCESSOR_SIGNATURE       1
+#define CPUID_XFAM              0x0ff00000
+#define CPUID_XFAM_K8           0x00000000
+#define CPUID_XFAM_10H          0x00100000
+#define CPUID_XFAM_11H          0x00200000
+#define CPUID_XMOD              0x000f0000
+#define CPUID_XMOD_REV_F        0x00040000
+
+/* AMD systems with C1E don't have a working lAPIC timer. Check for that. */
+static __cpuinit int amd_apic_timer_broken(void)
+{
+        u32 lo, hi, eax = cpuid_eax(CPUID_PROCESSOR_SIGNATURE);
+
+        switch (eax & CPUID_XFAM) {
+        case CPUID_XFAM_K8:
+                if ((eax & CPUID_XMOD) < CPUID_XMOD_REV_F)
+                        break;
+        case CPUID_XFAM_10H:
+        case CPUID_XFAM_11H:
+                rdmsr(MSR_K8_ENABLE_C1E, lo, hi);
+                if (lo & ENABLE_C1E_MASK)
+                        return 1;
+                break;
+        default:
+                /* err on the side of caution */
+                return 1;
+        }
+        return 0;
+}
+
+
+void __cpuinit early_init_amd(struct cpuinfo_x86 *c)
+{
+	early_init_amd_mc(c);
+
+	/* c->x86_power is 8000_0007 edx. Bit 8 is constant TSC */
+	if (c->x86_power & (1<<8))
+		set_cpu_cap(c, X86_FEATURE_CONSTANT_TSC);
+}
+
+/*
+ * On a AMD dual core setup the lower bits of the APIC id distingush the cores.
+ * Assumes number of cores is a power of two.
+ */
+static void __cpuinit amd_detect_cmp(struct cpuinfo_x86 *c)
+{
+#ifdef CONFIG_SMP
+        unsigned bits;
+#ifdef CONFIG_NUMA
+        int cpu = smp_processor_id();
+        int node = 0;
+        unsigned apicid = hard_smp_processor_id();
+#endif
+        bits = c->x86_coreid_bits;
+
+        /* Low order bits define the core id (index of core in socket) */
+        c->cpu_core_id = c->initial_apicid & ((1 << bits)-1);
+        /* Convert the initial APIC ID into the socket ID */
+        c->phys_proc_id = c->initial_apicid >> bits;
+
+#ifdef CONFIG_NUMA
+        node = c->phys_proc_id;
+        if (apicid_to_node[apicid] != NUMA_NO_NODE)
+                node = apicid_to_node[apicid];
+        if (!node_online(node)) {
+                /* Two possibilities here:
+                   - The CPU is missing memory and no node was created.
+                   In that case try picking one from a nearby CPU
+                   - The APIC IDs differ from the HyperTransport node IDs
+                   which the K8 northbridge parsing fills in.
+                   Assume they are all increased by a constant offset,
+                   but in the same order as the HT nodeids.
+                   If that doesn't result in a usable node fall back to the
+                   path for the previous case.  */
+                int ht_nodeid = c->initial_apicid;
+
+                if (ht_nodeid >= 0 &&
+                    apicid_to_node[ht_nodeid] != NUMA_NO_NODE)
+                        node = apicid_to_node[ht_nodeid];
+                /* Pick a nearby node */
+                if (!node_online(node))
+                        node = nearby_node(apicid);
+        }
+        numa_set_node(cpu, node);
+
+        printk(KERN_INFO "CPU %d/%x -> Node %d\n", cpu, apicid, node);
+#endif
+#endif
+}
+
+
+void __cpuinit init_amd(struct cpuinfo_x86 *c)
+{
+	unsigned level;
+
+#ifdef CONFIG_SMP
+	unsigned long long value;
+
+	/*
+	 * Disable TLB flush filter by setting HWCR.FFDIS on K8
+	 * bit 6 of msr C001_0015
+	 *
+	 * Errata 63 for SH-B3 steppings
+	 * Errata 122 for all steppings (F+ have it disabled by default)
+	 */
+	if (c->x86 == 15) {
+		rdmsrl(MSR_K7_HWCR, value);
+		value |= 1 << 6;
+		wrmsrl(MSR_K7_HWCR, value);
+	}
+#endif
+
+	/*
+	 * Bit 31 in normal CPUID used for nonstandard 3DNow ID;
+	 * 3DNow is IDd by bit 31 in extended CPUID (1*32+31) anyway
+	 */
+	clear_cpu_cap(c, 0*32+31);
+
+	/* On C+ stepping K8 rep microcode works well for copy/memset */
+	level = cpuid_eax(1);
+	if (c->x86 == 15 && ((level >= 0x0f48 && level < 0x0f50) ||
+		level >= 0x0f58))
+		set_cpu_cap(c, X86_FEATURE_REP_GOOD);
+	if (c->x86 == 0x10 || c->x86 == 0x11)
+		set_cpu_cap(c, X86_FEATURE_REP_GOOD);
+
+	/* Enable workaround for FXSAVE leak */
+	if (c->x86 >= 6)
+		set_cpu_cap(c, X86_FEATURE_FXSAVE_LEAK);
+
+	level = get_model_name(c);
+	if (!level) {
+		switch (c->x86) {
+		case 15:
+			/* Should distinguish Models here, but this is only
+			a fallback anyways. */
+			strcpy(c->x86_model_id, "Hammer");
+			break;
+		}
+	}
+	display_cacheinfo(c);
+
+	/* Multi core CPU? */
+	if (c->extended_cpuid_level >= 0x80000008)
+		amd_detect_cmp(c);
+
+	if (c->extended_cpuid_level >= 0x80000006 &&
+		(cpuid_edx(0x80000006) & 0xf000))
+		num_cache_leaves = 4;
+	else
+		num_cache_leaves = 3;
+
+	if (c->x86 == 0xf || c->x86 == 0x10 || c->x86 == 0x11)
+		set_cpu_cap(c, X86_FEATURE_K8);
+
+	/* MFENCE stops RDTSC speculation */
+	set_cpu_cap(c, X86_FEATURE_MFENCE_RDTSC);
+
+	if (c->x86 == 0x10)
+		fam10h_check_enable_mmcfg();
+
+	if (amd_apic_timer_broken())
+		disable_apic_timer = 1;
+
+	if (c == &boot_cpu_data && c->x86 >= 0xf && c->x86 <= 0x11) {
+		unsigned long long tseg;
+
+		/*
+		 * Split up direct mapping around the TSEG SMM area.
+		 * Don't do it for gbpages because there seems very little
+		 * benefit in doing so.
+		 */
+		if (!rdmsrl_safe(MSR_K8_TSEG_ADDR, &tseg) &&
+		(tseg >> PMD_SHIFT) < (max_pfn_mapped >> (PMD_SHIFT-PAGE_SHIFT)))
+		set_memory_4k((unsigned long)__va(tseg), 1);
+	}
+}
+
+
+static struct cpu_dev amd_cpu_dev __cpuinitdata = {
+	.c_vendor	= "AMD",
+	.c_ident	= { "AuthenticAMD" },
+	.c_early_init	= early_init_amd,
+	.c_init		= init_amd,
+};
+
+cpu_vendor_dev_register(X86_VENDOR_AMD, &amd_cpu_dev);
diff --git a/arch/x86/kernel/setup_64.c b/arch/x86/kernel/setup_64.c
index ff62838..0414a0c 100644
--- a/arch/x86/kernel/setup_64.c
+++ b/arch/x86/kernel/setup_64.c
@@ -96,8 +96,6 @@ int bootloader_type;
 
 unsigned long saved_video_mode;
 
-int force_mwait __cpuinitdata;
-
 /*
  * Early DMI memory
  */
@@ -526,7 +524,7 @@ void __init setup_arch(char **cmdline_p)
 	check_enable_amd_mmconf_dmi();
 }
 
-static int __cpuinit get_model_name(struct cpuinfo_x86 *c)
+int __cpuinit get_model_name(struct cpuinfo_x86 *c)
 {
 	unsigned int *v;
 
@@ -542,7 +540,7 @@ static int __cpuinit get_model_name(struct cpuinfo_x86 *c)
 }
 
 
-static void __cpuinit display_cacheinfo(struct cpuinfo_x86 *c)
+void __cpuinit display_cacheinfo(struct cpuinfo_x86 *c)
 {
 	unsigned int n, dummy, eax, ebx, ecx, edx;
 
@@ -574,227 +572,6 @@ static void __cpuinit display_cacheinfo(struct cpuinfo_x86 *c)
 	}
 }
 
-#ifdef CONFIG_NUMA
-static int __cpuinit nearby_node(int apicid)
-{
-	int i, node;
-
-	for (i = apicid - 1; i >= 0; i--) {
-		node = apicid_to_node[i];
-		if (node != NUMA_NO_NODE && node_online(node))
-			return node;
-	}
-	for (i = apicid + 1; i < MAX_LOCAL_APIC; i++) {
-		node = apicid_to_node[i];
-		if (node != NUMA_NO_NODE && node_online(node))
-			return node;
-	}
-	return first_node(node_online_map); /* Shouldn't happen */
-}
-#endif
-
-/*
- * On a AMD dual core setup the lower bits of the APIC id distingush the cores.
- * Assumes number of cores is a power of two.
- */
-static void __cpuinit amd_detect_cmp(struct cpuinfo_x86 *c)
-{
-#ifdef CONFIG_SMP
-	unsigned bits;
-#ifdef CONFIG_NUMA
-	int cpu = smp_processor_id();
-	int node = 0;
-	unsigned apicid = hard_smp_processor_id();
-#endif
-	bits = c->x86_coreid_bits;
-
-	/* Low order bits define the core id (index of core in socket) */
-	c->cpu_core_id = c->initial_apicid & ((1 << bits)-1);
-	/* Convert the initial APIC ID into the socket ID */
-	c->phys_proc_id = c->initial_apicid >> bits;
-
-#ifdef CONFIG_NUMA
-	node = c->phys_proc_id;
-	if (apicid_to_node[apicid] != NUMA_NO_NODE)
-		node = apicid_to_node[apicid];
-	if (!node_online(node)) {
-		/* Two possibilities here:
-		   - The CPU is missing memory and no node was created.
-		   In that case try picking one from a nearby CPU
-		   - The APIC IDs differ from the HyperTransport node IDs
-		   which the K8 northbridge parsing fills in.
-		   Assume they are all increased by a constant offset,
-		   but in the same order as the HT nodeids.
-		   If that doesn't result in a usable node fall back to the
-		   path for the previous case.  */
-
-		int ht_nodeid = c->initial_apicid;
-
-		if (ht_nodeid >= 0 &&
-		    apicid_to_node[ht_nodeid] != NUMA_NO_NODE)
-			node = apicid_to_node[ht_nodeid];
-		/* Pick a nearby node */
-		if (!node_online(node))
-			node = nearby_node(apicid);
-	}
-	numa_set_node(cpu, node);
-
-	printk(KERN_INFO "CPU %d/%x -> Node %d\n", cpu, apicid, node);
-#endif
-#endif
-}
-
-static void __cpuinit early_init_amd_mc(struct cpuinfo_x86 *c)
-{
-#ifdef CONFIG_SMP
-	unsigned bits, ecx;
-
-	/* Multi core CPU? */
-	if (c->extended_cpuid_level < 0x80000008)
-		return;
-
-	ecx = cpuid_ecx(0x80000008);
-
-	c->x86_max_cores = (ecx & 0xff) + 1;
-
-	/* CPU telling us the core id bits shift? */
-	bits = (ecx >> 12) & 0xF;
-
-	/* Otherwise recompute */
-	if (bits == 0) {
-		while ((1 << bits) < c->x86_max_cores)
-			bits++;
-	}
-
-	c->x86_coreid_bits = bits;
-
-#endif
-}
-
-#define ENABLE_C1E_MASK		0x18000000
-#define CPUID_PROCESSOR_SIGNATURE	1
-#define CPUID_XFAM		0x0ff00000
-#define CPUID_XFAM_K8		0x00000000
-#define CPUID_XFAM_10H		0x00100000
-#define CPUID_XFAM_11H		0x00200000
-#define CPUID_XMOD		0x000f0000
-#define CPUID_XMOD_REV_F	0x00040000
-
-/* AMD systems with C1E don't have a working lAPIC timer. Check for that. */
-static __cpuinit int amd_apic_timer_broken(void)
-{
-	u32 lo, hi, eax = cpuid_eax(CPUID_PROCESSOR_SIGNATURE);
-
-	switch (eax & CPUID_XFAM) {
-	case CPUID_XFAM_K8:
-		if ((eax & CPUID_XMOD) < CPUID_XMOD_REV_F)
-			break;
-	case CPUID_XFAM_10H:
-	case CPUID_XFAM_11H:
-		rdmsr(MSR_K8_ENABLE_C1E, lo, hi);
-		if (lo & ENABLE_C1E_MASK)
-			return 1;
-		break;
-	default:
-		/* err on the side of caution */
-		return 1;
-	}
-	return 0;
-}
-
-static void __cpuinit early_init_amd(struct cpuinfo_x86 *c)
-{
-	early_init_amd_mc(c);
-
- 	/* c->x86_power is 8000_0007 edx. Bit 8 is constant TSC */
-	if (c->x86_power & (1<<8))
-		set_cpu_cap(c, X86_FEATURE_CONSTANT_TSC);
-}
-
-static void __cpuinit init_amd(struct cpuinfo_x86 *c)
-{
-	unsigned level;
-
-#ifdef CONFIG_SMP
-	unsigned long value;
-
-	/*
-	 * Disable TLB flush filter by setting HWCR.FFDIS on K8
-	 * bit 6 of msr C001_0015
-	 *
-	 * Errata 63 for SH-B3 steppings
-	 * Errata 122 for all steppings (F+ have it disabled by default)
-	 */
-	if (c->x86 == 15) {
-		rdmsrl(MSR_K8_HWCR, value);
-		value |= 1 << 6;
-		wrmsrl(MSR_K8_HWCR, value);
-	}
-#endif
-
-	/* Bit 31 in normal CPUID used for nonstandard 3DNow ID;
-	   3DNow is IDd by bit 31 in extended CPUID (1*32+31) anyway */
-	clear_cpu_cap(c, 0*32+31);
-
-	/* On C+ stepping K8 rep microcode works well for copy/memset */
-	level = cpuid_eax(1);
-	if (c->x86 == 15 && ((level >= 0x0f48 && level < 0x0f50) ||
-			     level >= 0x0f58))
-		set_cpu_cap(c, X86_FEATURE_REP_GOOD);
-	if (c->x86 == 0x10 || c->x86 == 0x11)
-		set_cpu_cap(c, X86_FEATURE_REP_GOOD);
-
-	/* Enable workaround for FXSAVE leak */
-	if (c->x86 >= 6)
-		set_cpu_cap(c, X86_FEATURE_FXSAVE_LEAK);
-
-	level = get_model_name(c);
-	if (!level) {
-		switch (c->x86) {
-		case 15:
-			/* Should distinguish Models here, but this is only
-			   a fallback anyways. */
-			strcpy(c->x86_model_id, "Hammer");
-			break;
-		}
-	}
-	display_cacheinfo(c);
-
-	/* Multi core CPU? */
-	if (c->extended_cpuid_level >= 0x80000008)
-		amd_detect_cmp(c);
-
-	if (c->extended_cpuid_level >= 0x80000006 &&
-		(cpuid_edx(0x80000006) & 0xf000))
-		num_cache_leaves = 4;
-	else
-		num_cache_leaves = 3;
-
-	if (c->x86 == 0xf || c->x86 == 0x10 || c->x86 == 0x11)
-		set_cpu_cap(c, X86_FEATURE_K8);
-
-	/* MFENCE stops RDTSC speculation */
-	set_cpu_cap(c, X86_FEATURE_MFENCE_RDTSC);
-
-	if (c->x86 == 0x10)
-		fam10h_check_enable_mmcfg();
-
-	if (amd_apic_timer_broken())
-		disable_apic_timer = 1;
-
-	if (c == &boot_cpu_data && c->x86 >= 0xf && c->x86 <= 0x11) {
-		unsigned long long tseg;
-
-		/*
-		 * Split up direct mapping around the TSEG SMM area.
-		 * Don't do it for gbpages because there seems very little
-		 * benefit in doing so.
-		 */
-		if (!rdmsrl_safe(MSR_K8_TSEG_ADDR, &tseg) &&
-		(tseg >> PMD_SHIFT) < (max_pfn_mapped >> (PMD_SHIFT-PAGE_SHIFT)))
-			set_memory_4k((unsigned long)__va(tseg), 1);
-	}
-}
 
 void __cpuinit detect_ht(struct cpuinfo_x86 *c)
 {
@@ -978,6 +755,10 @@ static void __cpuinit get_cpu_vendor(struct cpuinfo_x86 *c)
 		c->x86_vendor = X86_VENDOR_UNKNOWN;
 }
 
+// FIXME: Needs to use cpu_vendor_dev_register
+extern void __cpuinit early_init_amd(struct cpuinfo_x86 *c);
+extern void __cpuinit init_amd(struct cpuinfo_x86 *c);
+
 /* Do some early cpuid on the boot CPU to get some parameter that are
    needed before check_bugs. Everything advanced is in identify_cpu
    below. */
-- 
http://www.codemonkey.org.uk

^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20 19:18       ` Dave Jones
@ 2008-05-20 19:42         ` H. Peter Anvin
  2008-05-21 23:55         ` H. Peter Anvin
  1 sibling, 0 replies; 10+ messages in thread
From: H. Peter Anvin @ 2008-05-20 19:42 UTC (permalink / raw)
  To: Dave Jones, H. Peter Anvin, Linux Kernel, Ingo Molnar, Thomas Gleixner

Dave Jones wrote:
> 
> Moving along the same direction..  Moving the vendor specific bits out of setup_64.c
> into cpu/ would go a long way towards killing of setup64.c.  I took a first pass at doing this
> in the diff below. So far I only looked at the AMD specific bits, and haven't done
> a complete conversion to cpu_dev style initialisation as done on 32bit, but that
> can easily be performed later after moving all the code out into its respective places.
> (downside: a bunch of externs in the interim).
> 
> comments on this before I go any further?
> 

Looks good to me at first glance, and would definitely be a good step on 
the way.

	-hpa

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-20 19:18       ` Dave Jones
  2008-05-20 19:42         ` H. Peter Anvin
@ 2008-05-21 23:55         ` H. Peter Anvin
  2008-05-22 14:04           ` Dave Jones
  1 sibling, 1 reply; 10+ messages in thread
From: H. Peter Anvin @ 2008-05-21 23:55 UTC (permalink / raw)
  To: Dave Jones, H. Peter Anvin, Linux Kernel, Ingo Molnar, Thomas Gleixner

Dave Jones wrote:
> 
> Moving along the same direction..  Moving the vendor specific bits out of setup_64.c
> into cpu/ would go a long way towards killing of setup64.c.  I took a first pass at doing this
> in the diff below. So far I only looked at the AMD specific bits, and haven't done
> a complete conversion to cpu_dev style initialisation as done on 32bit, but that
> can easily be performed later after moving all the code out into its respective places.
> (downside: a bunch of externs in the interim).
> 
> comments on this before I go any further?
> 

Hi Dave,

I was going to pull this into -tip, but I need a Signed-off-by: line in 
order to do so.  Could you resend this so we can add it to -tip?

	-hpa

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [X86] Remove unnecessary code in 64bit CPU identification.
  2008-05-21 23:55         ` H. Peter Anvin
@ 2008-05-22 14:04           ` Dave Jones
  0 siblings, 0 replies; 10+ messages in thread
From: Dave Jones @ 2008-05-22 14:04 UTC (permalink / raw)
  To: H. Peter Anvin; +Cc: Linux Kernel, Ingo Molnar, Thomas Gleixner

On Wed, May 21, 2008 at 04:55:28PM -0700, H. Peter Anvin wrote:
 > Dave Jones wrote:
 > > 
 > > Moving along the same direction..  Moving the vendor specific bits out of setup_64.c
 > > into cpu/ would go a long way towards killing of setup64.c.  I took a first pass at doing this
 > > in the diff below. So far I only looked at the AMD specific bits, and haven't done
 > > a complete conversion to cpu_dev style initialisation as done on 32bit, but that
 > > can easily be performed later after moving all the code out into its respective places.
 > > (downside: a bunch of externs in the interim).
 > > 
 > > comments on this before I go any further?
 > > 
 > 
 > Hi Dave,
 > 
 > I was going to pull this into -tip, but I need a Signed-off-by: line in 
 > order to do so.  Could you resend this so we can add it to -tip?

Yeah, I was going to rediff against tip and resend them, but I went
into the office instead yesterday, where nothing productive ever happens :-)

I'll get to it today.

	Dave

-- 
http://www.codemonkey.org.uk

^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2008-05-22 16:40 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2008-05-20  4:09 [X86] Remove unnecessary code in 64bit CPU identification Dave Jones
2008-05-20  4:14 ` Dave Jones
2008-05-20 14:46 ` H. Peter Anvin
2008-05-20 15:16   ` Dave Jones
2008-05-20 17:58     ` H. Peter Anvin
2008-05-20 18:06       ` Dave Jones
2008-05-20 19:18       ` Dave Jones
2008-05-20 19:42         ` H. Peter Anvin
2008-05-21 23:55         ` H. Peter Anvin
2008-05-22 14:04           ` Dave Jones

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).