]> git.kernelconcepts.de Git - karo-tx-linux.git/commitdiff
hwmon: (k8temp) Differentiate between AM2 and ASB1
authorAndreas Herrmann <andreas.herrmann3@amd.com>
Wed, 25 Aug 2010 13:42:12 +0000 (15:42 +0200)
committerGreg Kroah-Hartman <gregkh@suse.de>
Mon, 20 Sep 2010 20:17:43 +0000 (13:17 -0700)
commit a05e93f3b3fc2f53c1d0de3b17019e207c482349 upstream.

Commit 8bf0223ed515be24de0c671eedaff49e78bebc9c (hwmon, k8temp: Fix
temperature reporting for ASB1 processor revisions) fixed temperature
reporting for ASB1 CPUs. But those CPU models (model 0x6b, 0x6f, 0x7f)
were packaged both as AM2 (desktop) and ASB1 (mobile). Thus the commit
leads to wrong temperature reporting for AM2 CPU parts.

The solution is to determine the package type for models 0x6b, 0x6f,
0x7f.

This is done using BrandId from CPUID Fn8000_0001_EBX[15:0]. See
"Constructing the processor Name String" in "Revision Guide for AMD
NPT Family 0Fh Processors" (Rev. 3.46).

Cc: Rudolf Marek <r.marek@assembler.cz>
Reported-by: Vladislav Guberinic <neosisani@gmail.com>
Signed-off-by: Andreas Herrmann <andreas.herrmann3@amd.com>
Signed-off-by: Jean Delvare <khali@linux-fr.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
drivers/hwmon/k8temp.c

index f808d188afa3bfdbe4ae394ee72e8a6d14c5570c..4f84d1a76d52ae10d76b7e2af85e16359df2f98d 100644 (file)
@@ -143,6 +143,37 @@ static struct pci_device_id k8temp_ids[] = {
 
 MODULE_DEVICE_TABLE(pci, k8temp_ids);
 
+static int __devinit is_rev_g_desktop(u8 model)
+{
+       u32 brandidx;
+
+       if (model < 0x69)
+               return 0;
+
+       if (model == 0xc1 || model == 0x6c || model == 0x7c)
+               return 0;
+
+       /*
+        * Differentiate between AM2 and ASB1.
+        * See "Constructing the processor Name String" in "Revision
+        * Guide for AMD NPT Family 0Fh Processors" (33610).
+        */
+       brandidx = cpuid_ebx(0x80000001);
+       brandidx = (brandidx >> 9) & 0x1f;
+
+       /* Single core */
+       if ((model == 0x6f || model == 0x7f) &&
+           (brandidx == 0x7 || brandidx == 0x9 || brandidx == 0xc))
+               return 0;
+
+       /* Dual core */
+       if (model == 0x6b &&
+           (brandidx == 0xb || brandidx == 0xc))
+               return 0;
+
+       return 1;
+}
+
 static int __devinit k8temp_probe(struct pci_dev *pdev,
                                  const struct pci_device_id *id)
 {
@@ -179,9 +210,7 @@ static int __devinit k8temp_probe(struct pci_dev *pdev,
                                 "wrong - check erratum #141\n");
                }
 
-               if ((model >= 0x69) &&
-                   !(model == 0xc1 || model == 0x6c || model == 0x7c ||
-                     model == 0x6b || model == 0x6f || model == 0x7f)) {
+               if (is_rev_g_desktop(model)) {
                        /*
                         * RevG desktop CPUs (i.e. no socket S1G1 or
                         * ASB1 parts) need additional offset,