diff options
author | Harald Welte <laforge@openmoko.org> | 2008-11-19 17:11:00 +0000 |
---|---|---|
committer | Andy Green <agreen@pads.home.warmcat.com> | 2008-11-19 17:11:00 +0000 |
commit | d6456697fa63719b245bf1cfe35b77e6ac7fe63c (patch) | |
tree | 35a38f50fe27499d0a24495e3b2e535df8a04715 | |
parent | 1736f7caf067fac336181f7e59ba3b7aae1d7a9f (diff) |
glamo_fb: Implement screen blanking
This patch implements fb_blank() for the glamo-fb driver, which switches off
the pixel clock (DCLK) for power saving.
We currently delay the actual pixel clock switch until we enter
FB_BLANK_POWERDOWN, since the backlight fade is slow and we don't want the
user to see artefacts on the screen while the backlight is fading out.
So since the X server first sends FB_BLANK_{V,H}SYNC_SUSPEND, we start the
backlight fade here, and only once we get FB_BLANK_POWERDOWN the pixel clock is
disabled.
There are no measurements yet, but the power savings should be double, since
there is no longer any generation of the high-frequency LCM signals, and
there are no video-related SDRAM accesses anymore.
Signed-off-by: Harald Welte <laforge@openmoko.org>
-rw-r--r-- | drivers/mfd/glamo/glamo-core.c | 32 | ||||
-rw-r--r-- | drivers/mfd/glamo/glamo-core.h | 6 | ||||
-rw-r--r-- | drivers/mfd/glamo/glamo-fb.c | 29 |
3 files changed, 66 insertions, 1 deletions
diff --git a/drivers/mfd/glamo/glamo-core.c b/drivers/mfd/glamo/glamo-core.c index 0fea4f4ea0e..77e25a65a9b 100644 --- a/drivers/mfd/glamo/glamo-core.c +++ b/drivers/mfd/glamo/glamo-core.c @@ -526,6 +526,38 @@ int glamo_engine_disable(struct glamo_core *glamo, enum glamo_engine engine) } EXPORT_SYMBOL_GPL(glamo_engine_disable); +static const u_int16_t engine_clock_regs[__NUM_GLAMO_ENGINES] = { + [GLAMO_ENGINE_LCD] = GLAMO_REG_CLOCK_LCD, + [GLAMO_ENGINE_MMC] = GLAMO_REG_CLOCK_MMC, + [GLAMO_ENGINE_ISP] = GLAMO_REG_CLOCK_ISP, + [GLAMO_ENGINE_JPEG] = GLAMO_REG_CLOCK_JPEG, + [GLAMO_ENGINE_3D] = GLAMO_REG_CLOCK_3D, + [GLAMO_ENGINE_2D] = GLAMO_REG_CLOCK_2D, + [GLAMO_ENGINE_MPEG_ENC] = GLAMO_REG_CLOCK_MPEG, + [GLAMO_ENGINE_MPEG_DEC] = GLAMO_REG_CLOCK_MPEG, +}; + +void glamo_engine_clkreg_set(struct glamo_core *glamo, + enum glamo_engine engine, + u_int16_t mask, u_int16_t val) +{ + reg_set_bit_mask(glamo, engine_clock_regs[engine], mask, val); +} +EXPORT_SYMBOL_GPL(glamo_engine_clkreg_set); + +u_int16_t glamo_engine_clkreg_get(struct glamo_core *glamo, + enum glamo_engine engine) +{ + u_int16_t val; + + spin_lock(&glamo->lock); + val = __reg_read(glamo, engine_clock_regs[engine]); + spin_unlock(&glamo->lock); + + return val; +} +EXPORT_SYMBOL_GPL(glamo_engine_clkreg_get); + struct glamo_script reset_regs[] = { [GLAMO_ENGINE_LCD] = { GLAMO_REG_CLOCK_LCD, GLAMO_CLOCK_LCD_RESET diff --git a/drivers/mfd/glamo/glamo-core.h b/drivers/mfd/glamo/glamo-core.h index ce8d4c7e79e..4c52bc44eaf 100644 --- a/drivers/mfd/glamo/glamo-core.h +++ b/drivers/mfd/glamo/glamo-core.h @@ -96,4 +96,10 @@ void glamo_engine_reset(struct glamo_core *glamo, enum glamo_engine engine); int glamo_engine_reclock(struct glamo_core *glamo, enum glamo_engine engine, int ps); +void glamo_engine_clkreg_set(struct glamo_core *glamo, + enum glamo_engine engine, + u_int16_t mask, u_int16_t val); + +u_int16_t glamo_engine_clkreg_get(struct glamo_core *glamo, + enum glamo_engine engine); #endif /* __GLAMO_CORE_H */ diff --git a/drivers/mfd/glamo/glamo-fb.c b/drivers/mfd/glamo/glamo-fb.c index 0bc6a1be63f..1ae933e9a3e 100644 --- a/drivers/mfd/glamo/glamo-fb.c +++ b/drivers/mfd/glamo/glamo-fb.c @@ -422,7 +422,34 @@ static int glamofb_set_par(struct fb_info *info) static int glamofb_blank(int blank_mode, struct fb_info *info) { - /* FIXME */ + struct glamofb_handle *gfb = info->par; + struct glamo_core *gcore = gfb->mach_info->glamo; + + dev_dbg(gfb->dev, "glamofb_blank(%u)\n", blank_mode); + + switch (blank_mode) { + case FB_BLANK_VSYNC_SUSPEND: + case FB_BLANK_HSYNC_SUSPEND: + /* FIXME: add pdata hook/flag to indicate whether + * we should already switch off pixel clock here */ + break; + case FB_BLANK_POWERDOWN: + /* disable the pixel clock */ + glamo_engine_clkreg_set(gcore, GLAMO_ENGINE_LCD, + GLAMO_CLOCK_LCD_EN_DCLK, 0); + break; + case FB_BLANK_UNBLANK: + case FB_BLANK_NORMAL: + /* enable the pixel clock */ + glamo_engine_clkreg_set(gcore, GLAMO_ENGINE_LCD, + GLAMO_CLOCK_LCD_EN_DCLK, + GLAMO_CLOCK_LCD_EN_DCLK); + break; + } + + /* FIXME: once we have proper clock management in glamo-core, + * we can determine if other units need MCLK1 or the PLL, and + * disable it if not used. */ return 0; } |