aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/ide
diff options
context:
space:
mode:
authorAlbert Lee <albertcc@tw.ibm.com>2007-07-03 16:28:36 -0400
committerBartlomiej Zolnierkiewicz <bzolnier@gmail.com>2007-07-03 16:28:36 -0400
commit8006bf56e360a4db71d304df778870a371a9e930 (patch)
tree9471ba5fd85ce42c8ec6253893520371762e513e /drivers/ide
parent52374f890c1d0d64148d55a20d995a0b3e0ae987 (diff)
ide: pdc202xx_new PLL input clock fix
Recently the PLL input clock of Promise 2027x is sometimes detected higher than expected (e.g. 20.027 MHz compared to 16.714 MHz). It seems sometimes the mdelay() function is not as precise as it used to be. Per Alan's advice, HT or power management might affect the precision of mdelay(). This patch calls gettimeofday() to measure the time elapsed and calculate the PLL input clock accordingly. Signed-off-by: Albert Lee <albertcc@tw.ibm.com> Cc: Alan Cox <alan@lxorguk.ukuu.org.uk> Cc: Bahadir Balban <bahadir.balban@gmail.com> Acked-by: Sergei Shtylyov <sshtylyov@ru.mvista.com> Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Diffstat (limited to 'drivers/ide')
-rw-r--r--drivers/ide/pci/pdc202xx_new.c10
1 files changed, 8 insertions, 2 deletions
diff --git a/drivers/ide/pci/pdc202xx_new.c b/drivers/ide/pci/pdc202xx_new.c
index cc0bfdcf1f19..0765dce6948e 100644
--- a/drivers/ide/pci/pdc202xx_new.c
+++ b/drivers/ide/pci/pdc202xx_new.c
@@ -306,11 +306,13 @@ static long __devinit read_counter(u32 dma_base)
306 */ 306 */
307static long __devinit detect_pll_input_clock(unsigned long dma_base) 307static long __devinit detect_pll_input_clock(unsigned long dma_base)
308{ 308{
309 struct timeval start_time, end_time;
309 long start_count, end_count; 310 long start_count, end_count;
310 long pll_input; 311 long pll_input, usec_elapsed;
311 u8 scr1; 312 u8 scr1;
312 313
313 start_count = read_counter(dma_base); 314 start_count = read_counter(dma_base);
315 do_gettimeofday(&start_time);
314 316
315 /* Start the test mode */ 317 /* Start the test mode */
316 outb(0x01, dma_base + 0x01); 318 outb(0x01, dma_base + 0x01);
@@ -322,6 +324,7 @@ static long __devinit detect_pll_input_clock(unsigned long dma_base)
322 mdelay(10); 324 mdelay(10);
323 325
324 end_count = read_counter(dma_base); 326 end_count = read_counter(dma_base);
327 do_gettimeofday(&end_time);
325 328
326 /* Stop the test mode */ 329 /* Stop the test mode */
327 outb(0x01, dma_base + 0x01); 330 outb(0x01, dma_base + 0x01);
@@ -333,7 +336,10 @@ static long __devinit detect_pll_input_clock(unsigned long dma_base)
333 * Calculate the input clock in Hz 336 * Calculate the input clock in Hz
334 * (the clock counter is 30 bit wide and counts down) 337 * (the clock counter is 30 bit wide and counts down)
335 */ 338 */
336 pll_input = ((start_count - end_count) & 0x3ffffff) * 100; 339 usec_elapsed = (end_time.tv_sec - start_time.tv_sec) * 1000000 +
340 (end_time.tv_usec - start_time.tv_usec);
341 pll_input = ((start_count - end_count) & 0x3ffffff) / 10 *
342 (10000000 / usec_elapsed);
337 343
338 DBG("start[%ld] end[%ld]\n", start_count, end_count); 344 DBG("start[%ld] end[%ld]\n", start_count, end_count);
339 345