[PATCH] cpufreq bugfixes

From: Dominik Brodowski (linux@brodo.de)
Date: Sun Sep 29 2002 - 18:53:46 EST


Hi Linus,

Thanks for merging cpufreq. Please apply these bugfixes, too.

- incorrect pointer calculation spotted by Gerald Britton
- speedstep.c cleanup (Gerald Britton)

        Dominik

diff -ruN linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/elanfreq.c linux/arch/i386/kernel/cpu/cpufreq/elanfreq.c
--- linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/elanfreq.c Mon Sep 30 00:58:10 2002
+++ linux/arch/i386/kernel/cpu/cpufreq/elanfreq.c Mon Sep 30 01:43:06 2002
@@ -290,7 +290,7 @@
         if (!driver)
                 return -ENOMEM;
 
- driver->policy = (struct cpufreq_policy *) (driver + sizeof(struct cpufreq_driver));
+ driver->policy = (struct cpufreq_policy *) (driver + 1);
 
         if (!max_freq)
                 max_freq = elanfreq_get_cpu_frequency();
diff -ruN linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/longhaul.c linux/arch/i386/kernel/cpu/cpufreq/longhaul.c
--- linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/longhaul.c Mon Sep 30 00:58:10 2002
+++ linux/arch/i386/kernel/cpu/cpufreq/longhaul.c Mon Sep 30 01:43:06 2002
@@ -1,5 +1,5 @@
 /*
- * $Id: longhaul.c,v 1.70 2002/09/12 10:22:17 db Exp $
+ * $Id: longhaul.c,v 1.72 2002/09/29 23:43:10 db Exp $
  *
  * (C) 2001 Dave Jones. <davej@suse.de>
  * (C) 2002 Padraig Brady. <padraig@antefacto.com>
@@ -771,7 +771,7 @@
         if (!driver)
                 return -ENOMEM;
 
- driver->policy = (struct cpufreq_policy *) (driver + sizeof(struct cpufreq_driver));
+ driver->policy = (struct cpufreq_policy *) (driver + 1);
 
 #ifdef CONFIG_CPU_FREQ_24_API
         driver->cpu_min_freq = (unsigned int) lowest_speed;
diff -ruN linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/longrun.c linux/arch/i386/kernel/cpu/cpufreq/longrun.c
--- linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/longrun.c Mon Sep 30 00:58:10 2002
+++ linux/arch/i386/kernel/cpu/cpufreq/longrun.c Mon Sep 30 01:43:06 2002
@@ -1,5 +1,5 @@
 /*
- * $Id: longrun.c,v 1.10 2002/09/22 09:01:41 db Exp $
+ * $Id: longrun.c,v 1.12 2002/09/29 23:43:10 db Exp $
  *
  * (C) 2002 Dominik Brodowski <linux@brodo.de>
  *
@@ -241,7 +241,7 @@
         if (!driver)
                 return -ENOMEM;
 
- driver->policy = (struct cpufreq_policy *) (driver + sizeof(struct cpufreq_driver));
+ driver->policy = (struct cpufreq_policy *) (driver + 1);
 
         if (longrun_determine_freqs(&longrun_low_freq, &longrun_high_freq)) {
                 kfree(driver);
diff -ruN linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/p4-clockmod.c linux/arch/i386/kernel/cpu/cpufreq/p4-clockmod.c
--- linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/p4-clockmod.c Mon Sep 30 00:58:10 2002
+++ linux/arch/i386/kernel/cpu/cpufreq/p4-clockmod.c Mon Sep 30 01:43:06 2002
@@ -225,7 +225,7 @@
         if (!driver)
                 return -ENOMEM;
 
- driver->policy = (struct cpufreq_policy *) (driver + sizeof(struct cpufreq_driver));
+ driver->policy = (struct cpufreq_policy *) (driver + 1);
 
         if (!stock_freq)
                 stock_freq = cpu_khz;
diff -ruN linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/powernow-k6.c linux/arch/i386/kernel/cpu/cpufreq/powernow-k6.c
--- linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/powernow-k6.c Mon Sep 30 00:58:10 2002
+++ linux/arch/i386/kernel/cpu/cpufreq/powernow-k6.c Mon Sep 30 01:43:06 2002
@@ -1,5 +1,5 @@
 /*
- * $Id: powernow-k6.c,v 1.31 2002/09/21 09:05:29 db Exp $
+ * $Id: powernow-k6.c,v 1.33 2002/09/29 23:43:11 db Exp $
  * This file was part of Powertweak Linux (http://powertweak.sf.net)
  * and is shared with the Linux Kernel module.
  *
@@ -239,7 +239,7 @@
                 release_region (POWERNOW_IOPORT, 16);
                 return -ENOMEM;
         }
- driver->policy = (struct cpufreq_policy *) (driver + sizeof(struct cpufreq_driver));
+ driver->policy = (struct cpufreq_policy *) (driver + 1);
 
 #ifdef CONFIG_CPU_FREQ_24_API
         driver->cpu_min_freq = busfreq * 20;
diff -ruN linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/speedstep.c linux/arch/i386/kernel/cpu/cpufreq/speedstep.c
--- linux-2539cpufreq/arch/i386/kernel/cpu/cpufreq/speedstep.c Mon Sep 30 01:04:47 2002
+++ linux/arch/i386/kernel/cpu/cpufreq/speedstep.c Mon Sep 30 01:43:06 2002
@@ -1,5 +1,5 @@
 /*
- * $Id: speedstep.c,v 1.50 2002/09/22 08:16:25 db Exp $
+ * $Id: speedstep.c,v 1.53 2002/09/29 23:43:11 db Exp $
  *
  * (C) 2001 Dave Jones, Arjan van de ven.
  * (C) 2002 Dominik Brodowski <linux@brodo.de>
@@ -91,6 +91,7 @@
  */
 static int speedstep_get_state (unsigned int *state)
 {
+ unsigned long flags;
         u32 pmbase;
         u8 value;
 
@@ -110,9 +111,9 @@
                         return -EIO;
 
                 /* read state */
- local_irq_disable();
+ local_irq_save(flags);
                 value = inb(pmbase + 0x50);
- local_irq_enable();
+ local_irq_restore(flags);
 
                 dprintk(KERN_DEBUG "cpufreq: read at pmbase 0x%x + 0x50 returned 0x%x\n", pmbase, value);
 
@@ -132,7 +133,7 @@
  *
  * Tries to change the SpeedStep state.
  */
-static void speedstep_set_state (unsigned int state)
+static void speedstep_set_state (unsigned int state, int notify)
 {
         u32 pmbase;
         u8 pm2_blk;
@@ -154,7 +155,8 @@
         freqs.new = (state == SPEEDSTEP_HIGH) ? speedstep_high_freq : speedstep_low_freq;
         freqs.cpu = CPUFREQ_ALL_CPUS; /* speedstep.c is UP only driver */
         
- cpufreq_notify_transition(&freqs, CPUFREQ_PRECHANGE);
+ if (notify)
+ cpufreq_notify_transition(&freqs, CPUFREQ_PRECHANGE);
 
         switch (speedstep_chipset) {
         case SPEEDSTEP_CHIPSET_ICH2M:
@@ -173,10 +175,11 @@
                         return;
                 }
 
+ /* Disable IRQs */
+ local_irq_save(flags);
+
                 /* read state */
- local_irq_disable();
                 value = inb(pmbase + 0x50);
- local_irq_enable();
 
                 dprintk(KERN_DEBUG "cpufreq: read at pmbase 0x%x + 0x50 returned 0x%x\n", pmbase, value);
 
@@ -186,10 +189,6 @@
 
                 dprintk(KERN_DEBUG "cpufreq: writing 0x%x to pmbase 0x%x + 0x50\n", value, pmbase);
 
- /* Disable IRQs */
- local_irq_save(flags);
- local_irq_disable();
-
                 /* Disable bus master arbitration */
                 pm2_blk = inb(pmbase + 0x20);
                 pm2_blk |= 0x01;
@@ -202,14 +201,11 @@
                 pm2_blk &= 0xfe;
                 outb(pm2_blk, (pmbase + 0x20));
 
- /* Enable IRQs */
- local_irq_enable();
- local_irq_restore(flags);
-
                 /* check if transition was sucessful */
- local_irq_disable();
                 value = inb(pmbase + 0x50);
- local_irq_enable();
+
+ /* Enable IRQs */
+ local_irq_restore(flags);
 
                 dprintk(KERN_DEBUG "cpufreq: read at pmbase 0x%x + 0x50 returned 0x%x\n", pmbase, value);
 
@@ -223,7 +219,8 @@
                 printk (KERN_ERR "cpufreq: setting CPU frequency on this chipset unsupported.\n");
         }
 
- cpufreq_notify_transition(&freqs, CPUFREQ_POSTCHANGE);
+ if (notify)
+ cpufreq_notify_transition(&freqs, CPUFREQ_POSTCHANGE);
 
         return;
 }
@@ -526,10 +523,13 @@
  */
 static int speedstep_detect_speeds (void)
 {
+ unsigned long flags;
         unsigned int state;
- unsigned int low = 0, high = 0;
         int i, result;
-
+
+ /* Disable irqs for entire detection process */
+ local_irq_save(flags);
+
         for (i=0; i<2; i++) {
                 /* read the current state */
                 result = speedstep_get_state(&state);
@@ -541,31 +541,30 @@
                         switch (speedstep_processor) {
                         case SPEEDSTEP_PROCESSOR_PIII_C:
                         case SPEEDSTEP_PROCESSOR_PIII_T:
- low = pentium3_get_frequency();
+ speedstep_low_freq = pentium3_get_frequency();
                                 break;
                         case SPEEDSTEP_PROCESSOR_P4M:
- low = pentium4_get_frequency();
+ speedstep_low_freq = pentium4_get_frequency();
                         }
- speedstep_set_state(SPEEDSTEP_HIGH);
+ speedstep_set_state(SPEEDSTEP_HIGH, 0);
                 } else {
                         switch (speedstep_processor) {
                         case SPEEDSTEP_PROCESSOR_PIII_C:
                         case SPEEDSTEP_PROCESSOR_PIII_T:
- high = pentium3_get_frequency();
+ speedstep_high_freq = pentium3_get_frequency();
                                 break;
                         case SPEEDSTEP_PROCESSOR_P4M:
- high = pentium4_get_frequency();
+ speedstep_high_freq = pentium4_get_frequency();
                         }
- speedstep_set_state(SPEEDSTEP_LOW);
+ speedstep_set_state(SPEEDSTEP_LOW, 0);
                 }
-
- if (!low || !high ||
- (speedstep_low_freq == speedstep_high_freq))
- return -EIO;
         }
 
- speedstep_low_freq = low;
- speedstep_high_freq = high;
+ local_irq_restore(flags);
+
+ if (!speedstep_low_freq || !speedstep_high_freq ||
+ (speedstep_low_freq == speedstep_high_freq))
+ return -EIO;
 
         return 0;
 }
@@ -583,16 +582,16 @@
                 return;
 
         if (policy->min > speedstep_low_freq)
- speedstep_set_state(SPEEDSTEP_HIGH);
+ speedstep_set_state(SPEEDSTEP_HIGH, 1);
         else {
                 if (policy->max < speedstep_high_freq)
- speedstep_set_state(SPEEDSTEP_LOW);
+ speedstep_set_state(SPEEDSTEP_LOW, 1);
                 else {
                         /* both frequency states are allowed */
                         if (policy->policy == CPUFREQ_POLICY_POWERSAVE)
- speedstep_set_state(SPEEDSTEP_LOW);
+ speedstep_set_state(SPEEDSTEP_LOW, 1);
                         else
- speedstep_set_state(SPEEDSTEP_HIGH);
+ speedstep_set_state(SPEEDSTEP_HIGH, 1);
                 }
         }
 }
@@ -649,7 +648,7 @@
                 return -ENODEV;
         }
 
- dprintk(KERN_INFO "cpufreq: Intel(R) SpeedStep(TM) support $Revision: 1.50 $\n");
+ dprintk(KERN_INFO "cpufreq: Intel(R) SpeedStep(TM) support $Revision: 1.53 $\n");
         dprintk(KERN_DEBUG "cpufreq: chipset 0x%x - processor 0x%x\n",
                speedstep_chipset, speedstep_processor);
 
@@ -659,8 +658,6 @@
                 return result;
 
         /* detect low and high frequency */
- speedstep_low_freq = 100000;
- speedstep_high_freq = 200000;
         result = speedstep_detect_speeds();
         if (result)
                 return result;
@@ -682,8 +679,8 @@
         if (!driver)
                 return -ENOMEM;
 
- driver->policy = (struct cpufreq_policy *) (driver + sizeof(struct cpufreq_driver));
-
+ driver->policy = (struct cpufreq_policy *) (driver + 1);
+
 #ifdef CONFIG_CPU_FREQ_24_API
         driver->cpu_min_freq = speedstep_low_freq;
         driver->cpu_cur_freq[0] = speed;
diff -ruN linux-2539cpufreq/arch/i386/kernel/time.c linux/arch/i386/kernel/time.c
--- linux-2539cpufreq/arch/i386/kernel/time.c Mon Sep 30 00:58:09 2002
+++ linux/arch/i386/kernel/time.c Mon Sep 30 01:08:11 2002
@@ -626,7 +626,7 @@
                 }
                 for (i=0; i<NR_CPUS; i++)
                         if ((freq->cpu == CPUFREQ_ALL_CPUS) || (freq->cpu == i))
- cpu_data[i].loops_per_jiffy = cpufreq_scale(loops_per_jiffy, freq->old, freq->new);
+ cpu_data[i].loops_per_jiffy = cpufreq_scale(cpu_data[i].loops_per_jiffy, freq->old, freq->new);
                 break;
 
         case CPUFREQ_POSTCHANGE:
@@ -637,7 +637,7 @@
                 }
                 for (i=0; i<NR_CPUS; i++)
                         if ((freq->cpu == CPUFREQ_ALL_CPUS) || (freq->cpu == i))
- cpu_data[i].loops_per_jiffy = cpufreq_scale(loops_per_jiffy, freq->old, freq->new);
+ cpu_data[i].loops_per_jiffy = cpufreq_scale(cpu_data[i].loops_per_jiffy, freq->old, freq->new);
                 break;
         }
 
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/



This archive was generated by hypermail 2b29 : Mon Sep 30 2002 - 22:00:43 EST