Selaa lähdekoodia

[ARM] 3616/1: fix timer handler wrap logic for a number of platforms

Patch from Lennert Buytenhek

A couple of platforms aren't using the right comparison type in their
timer interrupt handlers (as we're comparing two wrapping timestamps,
we need a bmi/bpl-type comparison, not an unsigned comparison) -- this
patch fixes them up.

Signed-off-by: Lennert Buytenhek <buytenh@wantstofly.org>
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Lennert Buytenhek 19 vuotta sitten
vanhempi
commit
f869afab8f

+ 2 - 1
arch/arm/mach-ep93xx/core.c

@@ -103,7 +103,8 @@ static int ep93xx_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
 	write_seqlock(&xtime_lock);
 	write_seqlock(&xtime_lock);
 
 
 	__raw_writel(1, EP93XX_TIMER1_CLEAR);
 	__raw_writel(1, EP93XX_TIMER1_CLEAR);
-	while (__raw_readl(EP93XX_TIMER4_VALUE_LOW) - last_jiffy_time
+	while ((signed long)
+		(__raw_readl(EP93XX_TIMER4_VALUE_LOW) - last_jiffy_time)
 						>= TIMER4_TICKS_PER_JIFFY) {
 						>= TIMER4_TICKS_PER_JIFFY) {
 		last_jiffy_time += TIMER4_TICKS_PER_JIFFY;
 		last_jiffy_time += TIMER4_TICKS_PER_JIFFY;
 		timer_tick(regs);
 		timer_tick(regs);

+ 2 - 1
arch/arm/mach-ixp2000/core.c

@@ -211,7 +211,8 @@ static int ixp2000_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
 	/* clear timer 1 */
 	/* clear timer 1 */
 	ixp2000_reg_wrb(IXP2000_T1_CLR, 1);
 	ixp2000_reg_wrb(IXP2000_T1_CLR, 1);
 
 
-	while ((next_jiffy_time - *missing_jiffy_timer_csr) > ticks_per_jiffy) {
+	while ((signed long)(next_jiffy_time - *missing_jiffy_timer_csr)
+							>= ticks_per_jiffy) {
 		timer_tick(regs);
 		timer_tick(regs);
 		next_jiffy_time -= ticks_per_jiffy;
 		next_jiffy_time -= ticks_per_jiffy;
 	}
 	}

+ 2 - 2
arch/arm/mach-ixp23xx/core.c

@@ -334,7 +334,7 @@ void __init ixp23xx_init_irq(void)
 /*************************************************************************
 /*************************************************************************
  * Timer-tick functions for IXP23xx
  * Timer-tick functions for IXP23xx
  *************************************************************************/
  *************************************************************************/
-#define CLOCK_TICKS_PER_USEC	CLOCK_TICK_RATE / (USEC_PER_SEC)
+#define CLOCK_TICKS_PER_USEC	(CLOCK_TICK_RATE / USEC_PER_SEC)
 
 
 static unsigned long next_jiffy_time;
 static unsigned long next_jiffy_time;
 
 
@@ -353,7 +353,7 @@ ixp23xx_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
 {
 {
 	/* Clear Pending Interrupt by writing '1' to it */
 	/* Clear Pending Interrupt by writing '1' to it */
 	*IXP23XX_TIMER_STATUS = IXP23XX_TIMER1_INT_PEND;
 	*IXP23XX_TIMER_STATUS = IXP23XX_TIMER1_INT_PEND;
-	while ((*IXP23XX_TIMER_CONT - next_jiffy_time) > LATCH) {
+	while ((signed long)(*IXP23XX_TIMER_CONT - next_jiffy_time) >= LATCH) {
 		timer_tick(regs);
 		timer_tick(regs);
 		next_jiffy_time += LATCH;
 		next_jiffy_time += LATCH;
 	}
 	}

+ 1 - 1
arch/arm/mach-ixp4xx/common.c

@@ -276,7 +276,7 @@ static irqreturn_t ixp4xx_timer_interrupt(int irq, void *dev_id, struct pt_regs
 	/*
 	/*
 	 * Catch up with the real idea of time
 	 * Catch up with the real idea of time
 	 */
 	 */
-	while ((*IXP4XX_OSTS - last_jiffy_time) > LATCH) {
+	while ((signed long)(*IXP4XX_OSTS - last_jiffy_time) >= LATCH) {
 		timer_tick(regs);
 		timer_tick(regs);
 		last_jiffy_time += LATCH;
 		last_jiffy_time += LATCH;
 	}
 	}

+ 2 - 1
arch/arm/plat-omap/timer32k.c

@@ -210,7 +210,8 @@ static irqreturn_t omap_32k_timer_interrupt(int irq, void *dev_id,
 
 
 	now = omap_32k_sync_timer_read();
 	now = omap_32k_sync_timer_read();
 
 
-	while (now - omap_32k_last_tick >= OMAP_32K_TICKS_PER_HZ) {
+	while ((signed long)(now - omap_32k_last_tick)
+						>= OMAP_32K_TICKS_PER_HZ) {
 		omap_32k_last_tick += OMAP_32K_TICKS_PER_HZ;
 		omap_32k_last_tick += OMAP_32K_TICKS_PER_HZ;
 		timer_tick(regs);
 		timer_tick(regs);
 	}
 	}