diff options
author | Matt Hsu <matt_hsu@openmoko.org> | 2008-11-19 17:09:41 +0000 |
---|---|---|
committer | Andy Green <agreen@pads.home.warmcat.com> | 2008-11-19 17:09:41 +0000 |
commit | 13a6a30e83edf90374d5ce4e336315a96ebf394d (patch) | |
tree | ad9cdbedc012e058d62b50583f38f2d37eb77a23 | |
parent | 8b6c3b85838ec2cc1e4ad9231f7fe59be7b8ccfe (diff) |
From cc08b5986dfd8d971ee46ce7045fb7863f99a92a Mon Sep 17 00:00:00 2001
Subject: [PATCH] - add suspend/resume function of s3c24xx_hcd driver
Signed-off-by: Matt Hsu <matt_hsu@openmoko.org>
-rw-r--r-- | drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.c | 65 | ||||
-rw-r--r-- | drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.h | 14 |
2 files changed, 79 insertions, 0 deletions
diff --git a/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.c b/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.c index af0066d9a96..fdc69a0f6a3 100644 --- a/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.c +++ b/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.c @@ -1365,11 +1365,76 @@ static int s3c24xx_hcd_remove(struct platform_device * pdev) { return 0; } +#ifdef CONFIG_PM + +static int s3c24xx_hcd_suspend(struct platform_device * pdev) +{ + struct s3c24xx_hcd_context * context = &hcd_context; + unsigned long flags; + + spin_lock_irqsave(&context->lock, flags); + + context->suspend_regs.con = readl(context->base + S3C2410_SDICON); + context->suspend_regs.pre = readl(context->base + S3C2410_SDIPRE); + context->suspend_regs.cmdarg = readl(context->base + S3C2410_SDICMDARG); + context->suspend_regs.cmdcon = readl(context->base + S3C2410_SDICMDCON); + context->suspend_regs.cmdsta = readl(context->base + S3C2410_SDICMDSTAT); + context->suspend_regs.r0 = readl(context->base + S3C2410_SDIRSP0); + context->suspend_regs.r1 = readl(context->base + S3C2410_SDIRSP1); + context->suspend_regs.r2 = readl(context->base + S3C2410_SDIRSP2); + context->suspend_regs.r3 = readl(context->base + S3C2410_SDIRSP3); + context->suspend_regs.timer = readl(context->base + S3C2410_SDITIMER); + context->suspend_regs.bsize = readl(context->base + S3C2410_SDIBSIZE); + context->suspend_regs.datcon = readl(context->base + S3C2410_SDIDCON); + context->suspend_regs.datcnt = readl(context->base + S3C2410_SDIDCNT); + context->suspend_regs.datsta = readl(context->base + S3C2410_SDIDSTA); + context->suspend_regs.fsta = readl(context->base + S3C2410_SDIFSTA); + context->suspend_regs.imask = readl(context->base + S3C2440_SDIIMSK); + + spin_unlock_irqrestore(&context->lock, flags); + return 0; +} + +static int s3c24xx_hcd_resume(struct platform_device * pdev) +{ + struct s3c24xx_hcd_context * context = &hcd_context; + unsigned long flags; + + spin_lock_irqsave(&context->lock, flags); + + writel(context->suspend_regs.con, context->base + S3C2410_SDICON); + writel(context->suspend_regs.pre, context->base + S3C2410_SDIPRE); + writel(context->suspend_regs.cmdarg, context->base + S3C2410_SDICMDARG); + writel(context->suspend_regs.cmdcon, context->base + S3C2410_SDICMDCON); + writel(context->suspend_regs.cmdsta, context->base + S3C2410_SDICMDSTAT); + writel(context->suspend_regs.r0, context->base + S3C2410_SDIRSP0); + writel(context->suspend_regs.r1, context->base + S3C2410_SDIRSP1); + writel(context->suspend_regs.r2, context->base + S3C2410_SDIRSP2); + writel(context->suspend_regs.r3, context->base + S3C2410_SDIRSP3); + writel(context->suspend_regs.timer, context->base + S3C2410_SDITIMER); + writel(context->suspend_regs.bsize, context->base + S3C2410_SDIBSIZE); + writel(context->suspend_regs.datcon, context->base + S3C2410_SDIDCON); + writel(context->suspend_regs.datcnt, context->base + S3C2410_SDIDCNT); + writel(context->suspend_regs.datsta, context->base + S3C2410_SDIDSTA); + writel(context->suspend_regs.fsta, context->base + S3C2410_SDIFSTA); + writel(context->suspend_regs.imask, context->base + S3C2440_SDIIMSK); + + spin_unlock_irqrestore(&context->lock, flags); + return 0; +} + +#else +#define s3c24xx_hcd_suspend = NULL +#define s3c24xx_hcd_resume = NULL +#endif + static struct platform_driver s3c24xx_hcd_sdio = { .driver.name = "s3c24xx-sdio", .probe = s3c24xx_hcd_probe, .remove = s3c24xx_hcd_remove, + .suspend = s3c24xx_hcd_suspend, + .resume = s3c24xx_hcd_resume, }; #ifdef CONFIG_DEBUG_FS diff --git a/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.h b/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.h index eb262fc4b25..47fdd331d6a 100644 --- a/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.h +++ b/drivers/sdio/hcd/s3c24xx/s3c24xx_hcd.h @@ -57,6 +57,20 @@ struct s3c24xx_hcd_context { struct work_struct io_work; struct work_struct irq_work; + +#ifdef CONFIG_PM + struct { + UINT32 con; + UINT32 pre; + UINT32 cmdarg, cmdcon, cmdsta; + UINT32 r0, r1, r2, r3; + UINT32 timer; + UINT32 bsize; + UINT32 datcon, datcnt, datsta; + UINT32 fsta; + UINT32 imask; + } suspend_regs; +#endif }; SDIO_STATUS s3c24xx_hcd_config(PSDHCD hcd, PSDCONFIG config); |