mirror of
git://projects.qi-hardware.com/openwrt-xburst.git
synced 2025-04-21 12:27:27 +03:00
change prefix for kernelpatchbase 2.6.26
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@13619 3c298f89-4303-0410-b956-a3cf2f4a3e73
This commit is contained in:
@@ -0,0 +1,128 @@
|
||||
From 1da7d81ddc35e3527d10abbc411bc09c81340d70 Mon Sep 17 00:00:00 2001
|
||||
From: warmcat <andy@warmcat.com>
|
||||
Date: Fri, 25 Jul 2008 23:06:00 +0100
|
||||
Subject: [PATCH] fix-s3c2410_timer_setup-resume-BUG.patch
|
||||
|
||||
---
|
||||
arch/arm/plat-s3c24xx/time.c | 33 +++++++++++++++++++++++++++++++++
|
||||
drivers/i2c/chips/pcf50633.c | 9 +++++++--
|
||||
2 files changed, 40 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/arch/arm/plat-s3c24xx/time.c b/arch/arm/plat-s3c24xx/time.c
|
||||
index f8d307b..59e5382 100644
|
||||
--- a/arch/arm/plat-s3c24xx/time.c
|
||||
+++ b/arch/arm/plat-s3c24xx/time.c
|
||||
@@ -42,6 +42,7 @@
|
||||
|
||||
static unsigned long timer_startval;
|
||||
static unsigned long timer_usec_ticks;
|
||||
+static struct work_struct resume_work;
|
||||
|
||||
#define TIMER_USEC_SHIFT 16
|
||||
|
||||
@@ -199,9 +200,12 @@ static void s3c2410_timer_setup (void)
|
||||
|
||||
pclk = clk_get_rate(clk);
|
||||
|
||||
+ printk("pclk = %d\n", pclk);
|
||||
+
|
||||
/* configure clock tick */
|
||||
|
||||
timer_usec_ticks = timer_mask_usec_ticks(6, pclk);
|
||||
+ printk("timer_usec_ticks = %d\n", timer_usec_ticks);
|
||||
|
||||
tcfg1 &= ~S3C2410_TCFG1_MUX4_MASK;
|
||||
tcfg1 |= S3C2410_TCFG1_MUX4_DIV2;
|
||||
@@ -210,6 +214,11 @@ static void s3c2410_timer_setup (void)
|
||||
tcfg0 |= ((6 - 1) / 2) << S3C2410_TCFG_PRESCALER1_SHIFT;
|
||||
|
||||
tcnt = (pclk / 6) / HZ;
|
||||
+
|
||||
+ /* start the timer running */
|
||||
+ tcon |= S3C2410_TCON_T4START | S3C2410_TCON_T4RELOAD;
|
||||
+ tcon &= ~S3C2410_TCON_T4MANUALUPD;
|
||||
+ __raw_writel(tcon, S3C2410_TCON);
|
||||
}
|
||||
|
||||
/* timers reload after counting zero, so reduce the count by 1 */
|
||||
@@ -245,10 +254,34 @@ static void s3c2410_timer_setup (void)
|
||||
tcon |= S3C2410_TCON_T4START;
|
||||
tcon &= ~S3C2410_TCON_T4MANUALUPD;
|
||||
__raw_writel(tcon, S3C2410_TCON);
|
||||
+
|
||||
+ __raw_writel(__raw_readl(S3C2410_INTMSK) & (~(1UL << 14)),
|
||||
+ S3C2410_INTMSK);
|
||||
+
|
||||
+}
|
||||
+
|
||||
+static void timer_resume_work(struct work_struct *work)
|
||||
+{
|
||||
+ s3c2410_timer_setup();
|
||||
+}
|
||||
+
|
||||
+/* ooh a nasty situation arises if we try to call s3c2410_timer_setup() from
|
||||
+ * the resume handler. It is called in atomic context but the clock APIs
|
||||
+ * try to lock a mutex which may sleep. We are in a bit of an unusual
|
||||
+ * situation because we don't have a tick source right now, but it should be
|
||||
+ * okay to try to schedule a work item... hopefully
|
||||
+ */
|
||||
+
|
||||
+static void s3c2410_timer_resume_atomic(void)
|
||||
+{
|
||||
+ int ret = schedule_work(&resume_work);
|
||||
+ if (!ret)
|
||||
+ printk(KERN_INFO"Failed to schedule_work tick ctr (%d)\n", ret);
|
||||
}
|
||||
|
||||
static void __init s3c2410_timer_init (void)
|
||||
{
|
||||
+ INIT_WORK(&resume_work, timer_resume_work);
|
||||
s3c2410_timer_setup();
|
||||
setup_irq(IRQ_TIMER4, &s3c2410_timer_irq);
|
||||
}
|
||||
diff --git a/drivers/i2c/chips/pcf50633.c b/drivers/i2c/chips/pcf50633.c
|
||||
index e23c540..91b9ac3 100644
|
||||
--- a/drivers/i2c/chips/pcf50633.c
|
||||
+++ b/drivers/i2c/chips/pcf50633.c
|
||||
@@ -1926,9 +1926,11 @@ static int pcf50633_resume(struct device *dev)
|
||||
struct pcf50633_data *pcf = i2c_get_clientdata(client);
|
||||
int i;
|
||||
|
||||
- mutex_lock(&pcf->lock);
|
||||
+ printk(KERN_INFO"a\n");
|
||||
+ /* mutex_lock(&pcf->lock); */ /* resume in atomic context */
|
||||
|
||||
__reg_write(pcf, PCF50633_REG_LEDENA, 0x01);
|
||||
+ printk(KERN_INFO"b\n");
|
||||
|
||||
/* Resume all saved registers that don't "survive" standby state */
|
||||
__reg_write(pcf, PCF50633_REG_INT1M, pcf->standby_regs.int1m);
|
||||
@@ -1936,6 +1938,7 @@ static int pcf50633_resume(struct device *dev)
|
||||
__reg_write(pcf, PCF50633_REG_INT3M, pcf->standby_regs.int3m);
|
||||
__reg_write(pcf, PCF50633_REG_INT4M, pcf->standby_regs.int4m);
|
||||
__reg_write(pcf, PCF50633_REG_INT5M, pcf->standby_regs.int5m);
|
||||
+ printk(KERN_INFO"c\n");
|
||||
|
||||
__reg_write(pcf, PCF50633_REG_OOCTIM2, pcf->standby_regs.ooctim2);
|
||||
__reg_write(pcf, PCF50633_REG_AUTOOUT, pcf->standby_regs.autoout);
|
||||
@@ -1949,14 +1952,16 @@ static int pcf50633_resume(struct device *dev)
|
||||
__reg_write(pcf, PCF50633_REG_LEDOUT, pcf->standby_regs.ledout);
|
||||
__reg_write(pcf, PCF50633_REG_LEDENA, pcf->standby_regs.ledena);
|
||||
__reg_write(pcf, PCF50633_REG_LEDDIM, pcf->standby_regs.leddim);
|
||||
+ printk(KERN_INFO"d\n");
|
||||
/* FIXME: one big read? */
|
||||
for (i = 0; i < 7; i++) {
|
||||
u_int8_t reg_out = PCF50633_REG_LDO1OUT + 2*i;
|
||||
__reg_write(pcf, reg_out, pcf->standby_regs.ldo[i].out);
|
||||
__reg_write(pcf, reg_out+1, pcf->standby_regs.ldo[i].ena);
|
||||
}
|
||||
+ printk(KERN_INFO"e\n");
|
||||
|
||||
- mutex_unlock(&pcf->lock);
|
||||
+ /* mutex_unlock(&pcf->lock); */ /* resume in atomic context */
|
||||
|
||||
pcf50633_irq(pcf->irq, pcf);
|
||||
|
||||
--
|
||||
1.5.6.3
|
||||
|
||||
Reference in New Issue
Block a user