* [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages
2008-07-13 13:26 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v5 Jaya Kumar
@ 2008-07-13 13:26 ` Jaya Kumar
2008-07-16 7:09 ` eric miao
0 siblings, 1 reply; 18+ messages in thread
From: Jaya Kumar @ 2008-07-13 13:26 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
This patch converts the printk messages in metronomefb to dev_dbg/err type
messages.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
drivers/video/metronomefb.c | 49 +++++++++++++++++++-----------------------
1 files changed, 22 insertions(+), 27 deletions(-)
diff --git a/drivers/video/metronomefb.c b/drivers/video/metronomefb.c
index cc4c038..8ccd113 100644
--- a/drivers/video/metronomefb.c
+++ b/drivers/video/metronomefb.c
@@ -18,6 +18,8 @@
* is provided as am200epd.c
*
*/
+#define DEBUG 1
+
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
@@ -40,15 +42,6 @@
#include <asm/unaligned.h>
-
-#define DEBUG 1
-#ifdef DEBUG
-#define DPRINTK(f, a...) printk(KERN_DEBUG "%s: " f, __func__ , ## a)
-#else
-#define DPRINTK(f, a...)
-#endif
-
-
/* Display specific information */
#define DPY_W 832
#define DPY_H 622
@@ -135,8 +128,8 @@ static u16 calc_img_cksum(u16 *start, int length)
/* here we decode the incoming waveform file and populate metromem */
#define EXP_WFORM_SIZE 47001
-static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
- u8 *frame_count)
+static int __devinit load_waveform(u8 *mem, size_t size, int m, int t,
+ struct metronomefb_par *par)
{
int tta;
int wmta;
@@ -148,9 +141,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
int wfm_idx, owfm_idx;
int mem_idx = 0;
struct waveform_hdr *wfm_hdr;
+ u8 *metromem = par->metromem_wfm;
+ struct device *dev = par->info->dev;
if (size != EXP_WFORM_SIZE) {
- printk(KERN_ERR "Error: unexpected size %d != %d\n", size,
+ dev_err(dev, "Error: unexpected size %d != %d\n", size,
EXP_WFORM_SIZE);
return -EINVAL;
}
@@ -158,16 +153,16 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
wfm_hdr = (struct waveform_hdr *) mem;
if (wfm_hdr->fvsn != 1) {
- printk(KERN_ERR "Error: bad fvsn %x\n", wfm_hdr->fvsn);
+ dev_err(dev, "Error: bad fvsn %x\n", wfm_hdr->fvsn);
return -EINVAL;
}
if (wfm_hdr->luts != 0) {
- printk(KERN_ERR "Error: bad luts %x\n", wfm_hdr->luts);
+ dev_err(dev, "Error: bad luts %x\n", wfm_hdr->luts);
return -EINVAL;
}
cksum = calc_cksum(32, 47, mem);
if (cksum != wfm_hdr->wfm_cs) {
- printk(KERN_ERR "Error: bad cksum %x != %x\n", cksum,
+ dev_err(dev, "Error: bad cksum %x != %x\n", cksum,
wfm_hdr->wfm_cs);
return -EINVAL;
}
@@ -175,7 +170,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
wfm_hdr->trc += 1;
for (i = 0; i < 5; i++) {
if (*(wfm_hdr->stuff2a + i) != 0) {
- printk(KERN_ERR "Error: unexpected value in padding\n");
+ dev_err(dev, "Error: unexpected value in padding\n");
return -EINVAL;
}
}
@@ -200,7 +195,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(sizeof(*wfm_hdr), cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad temperature range table cksum"
+ dev_err(dev, "Error: bad temperature range table cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -212,7 +207,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad mode table address cksum"
+ dev_err(dev, "Error: bad mode table address cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -224,7 +219,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad temperature table address cksum"
+ dev_err(dev, "Error: bad temperature table address cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -259,11 +254,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(owfm_idx, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad waveform data cksum"
+ dev_err(dev, "Error: bad waveform data cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
- *frame_count = (mem_idx/64);
+ par->frame_count = (mem_idx/64);
return 0;
}
@@ -662,15 +657,15 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
b) process waveform and decode into metromem */
retval = request_firmware(&fw_entry, "metronome.wbf", &dev->dev);
if (retval < 0) {
- printk(KERN_ERR "metronomefb: couldn't get waveform\n");
+ dev_err(&dev->dev, "Failed to get waveform\n");
goto err_dma_free;
}
- retval = load_waveform((u8 *) fw_entry->data, fw_entry->size,
- par->metromem_wfm, 3, 31, &par->frame_count);
+ retval = load_waveform((u8 *) fw_entry->data, fw_entry->size, 3, 31,
+ par);
release_firmware(fw_entry);
if (retval < 0) {
- printk(KERN_ERR "metronomefb: couldn't process waveform\n");
+ dev_err(&dev->dev, "Failed processing waveform\n");
goto err_dma_free;
}
@@ -688,7 +683,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
retval = fb_alloc_cmap(&info->cmap, 8, 0);
if (retval < 0) {
- printk(KERN_ERR "Failed to allocate colormap\n");
+ dev_err(&dev->dev, "Failed to allocate colormap\n");
goto err_fb_rel;
}
@@ -704,7 +699,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
platform_set_drvdata(dev, info);
- printk(KERN_INFO
+ dev_dbg(&dev->dev,
"fb%d: Metronome frame buffer device, using %dK of video"
" memory\n", info->node, videomemorysize >> 10);
--
1.5.3.6
-------------------------------------------------------------------------
Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages
2008-07-13 13:26 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
@ 2008-07-16 7:09 ` eric miao
0 siblings, 0 replies; 18+ messages in thread
From: eric miao @ 2008-07-16 7:09 UTC (permalink / raw)
To: Jaya Kumar; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Sun, Jul 13, 2008 at 9:26 PM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
> This patch converts the printk messages in metronomefb to dev_dbg/err type
> messages.
>
This is always a good thing to do :)
> Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
With the removal of "#define DEBUG 1",
Acked-by: Eric Miao <eric.miao@marvell.com>
> ---
> drivers/video/metronomefb.c | 49 +++++++++++++++++++-----------------------
> 1 files changed, 22 insertions(+), 27 deletions(-)
>
> diff --git a/drivers/video/metronomefb.c b/drivers/video/metronomefb.c
> index cc4c038..8ccd113 100644
> --- a/drivers/video/metronomefb.c
> +++ b/drivers/video/metronomefb.c
> @@ -18,6 +18,8 @@
> * is provided as am200epd.c
> *
> */
> +#define DEBUG 1
> +
Don't leave DEBUG in the final patch please.
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6
@ 2008-07-20 6:10 Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
` (4 more replies)
0 siblings, 5 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-20 6:10 UTC (permalink / raw)
To: ymiao3; +Cc: linux-fbdev-devel, linux-arm-kernel
Hi Eric, arm and fbdev friends,
This is version 6 of this RFC and contains the following updates:
- remove use of clk api for 32k clock and replace with check and set
in gumstix init code
- avoid exporting am200_device_fb and remove am200epd platform code
- allow am200epd to only be built as a built-in. This allows me to use
set_pxa_fb_info and removes related issues in other parts of the code.
- change the way we do setup_fb in am200epd so am200epd does not need to
wait for metronomefb to receive its waveform file from user space.
Thanks to Eric and Russell for feedback.
I will take out DEBUG before final.
This RFC consists of patches intended to improve the condition of the
am200epd devkit support. The am200epd devkit contains a gumstix (pxa255) and
a carrier board (am200epd or Lyre), and a metronome display controller.
Previously, there was a drivers/video/am200epd driver that manipulated pxa
LCDC registers and GPSR/GPLR registers directly. That was clearly wrong and
broken so I have removed it and written a new mach-pxa am200epd support
driver.This driver interfaces with pxafb through a set of callbacks to
share/unshare pxafb's framebuffer and achieves the same functionality without
manipulating any pxa registers directly. The patches are split as follows:
pxafb: add shared framebuffer interface
gumstix: conversion to MFP support and add bluetooth support
am200epd: convert to shared fb and use gpio api
metronomefb: convert printk to dev_dbg/err messages
metronomefb: changes to use separate framebuffer
I would be grateful for any feedback and advice.
Thanks,
jaya
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface
2008-07-20 6:10 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6 Jaya Kumar
@ 2008-07-20 6:10 ` Jaya Kumar
2008-07-21 11:11 ` Russell King - ARM Linux
2008-07-20 6:10 ` [RFC 2.6.26-rc9 2/5] gumstix: conversion to MFP support and add bluetooth support Jaya Kumar
` (3 subsequent siblings)
4 siblings, 1 reply; 18+ messages in thread
From: Jaya Kumar @ 2008-07-20 6:10 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
These changes are to make it possible for a secondary driver to share the
pxafb framebuffer. The changes include:
- adding custom_xfer_div entry so that a driver can have custom sized
transfers. For example, the metronome controller uses 16 bit AMLCD
transfers but actually has 3 bit pixels in 8 bit containers.
- adding extra_video_mem entry so that a driver can tell pxafb of its
additional needs.
- adding share_video_mem/unshare_video_mem callbacks to notify the secondary
driver of the framebuffer address, to allow refcounting, and to cleanup on
completion.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
drivers/video/pxafb.c | 46 ++++++++++++++++++++++++++++++++-----
include/asm-arm/arch-pxa/pxafb.h | 8 ++++++
2 files changed, 47 insertions(+), 7 deletions(-)
diff --git a/drivers/video/pxafb.c b/drivers/video/pxafb.c
index bb25143..d343675 100644
--- a/drivers/video/pxafb.c
+++ b/drivers/video/pxafb.c
@@ -57,6 +57,8 @@
*/
#define DEBUG_VAR 1
+static struct platform_driver pxafb_driver;
+
#include "pxafb.h"
/* Bits which should not be set in machine configuration structures */
@@ -826,10 +828,15 @@ int pxafb_smart_flush(struct fb_info *info)
static void setup_parallel_timing(struct pxafb_info *fbi,
struct fb_var_screeninfo *var)
{
+ struct pxafb_mach_info *inf = fbi->dev->platform_data;
unsigned int lines_per_panel, pcd = get_pcd(fbi, var->pixclock);
+ unsigned int pix_per_line = var->xres;
+
+ if (inf->custom_xfer_div)
+ pix_per_line /= inf->custom_xfer_div;
fbi->reg_lccr1 =
- LCCR1_DisWdth(var->xres) +
+ LCCR1_DisWdth(pix_per_line) +
LCCR1_HorSnchWdth(var->hsync_len) +
LCCR1_BegLnDel(var->left_margin) +
LCCR1_EndLnDel(var->right_margin);
@@ -870,6 +877,7 @@ static int pxafb_activate_var(struct fb_var_screeninfo *var,
{
u_long flags;
size_t nbytes;
+ struct pxafb_mach_info *inf = fbi->dev->platform_data;
#if DEBUG_VAR
if (!(fbi->lccr0 & LCCR0_LCDT)) {
@@ -931,6 +939,8 @@ static int pxafb_activate_var(struct fb_var_screeninfo *var,
fbi->reg_lccr3 |= pxafb_bpp_to_lccr3(var);
nbytes = var->yres * fbi->fb.fix.line_length;
+ if (inf->custom_xfer_div)
+ nbytes /= inf->custom_xfer_div;
if ((fbi->lccr0 & LCCR0_SDS) == LCCR0_Dual) {
nbytes = nbytes / 2;
@@ -1304,21 +1314,25 @@ static int pxafb_resume(struct platform_device *dev)
* cache. Once this area is remapped, all virtual memory
* access to the video memory should occur at the new region.
*/
-static int __devinit pxafb_map_video_memory(struct pxafb_info *fbi)
+static int __devinit pxafb_map_video_memory(struct pxafb_info *fbi,
+ struct pxafb_mach_info *inf)
{
+ int ret;
/*
* We reserve one page for the palette, plus the size
* of the framebuffer.
*/
fbi->video_offset = PAGE_ALIGN(sizeof(struct pxafb_dma_buff));
- fbi->map_size = PAGE_ALIGN(fbi->fb.fix.smem_len + fbi->video_offset);
+ fbi->map_size = PAGE_ALIGN(fbi->fb.fix.smem_len + fbi->video_offset +
+ inf->extra_video_mem);
fbi->map_cpu = dma_alloc_writecombine(fbi->dev, fbi->map_size,
&fbi->map_dma, GFP_KERNEL);
if (fbi->map_cpu) {
/* prevent initial garbage on screen */
memset(fbi->map_cpu, 0, fbi->map_size);
- fbi->fb.screen_base = fbi->map_cpu + fbi->video_offset;
+ fbi->fb.screen_base = (char __force __iomem *) fbi->map_cpu
+ + fbi->video_offset;
fbi->screen_dma = fbi->map_dma + fbi->video_offset;
/*
@@ -1340,6 +1354,13 @@ static int __devinit pxafb_map_video_memory(struct pxafb_info *fbi)
fbi->smart_cmds = (uint16_t *) fbi->dma_buff->cmd_buff;
fbi->n_smart_cmds = 0;
#endif
+ if (inf->share_video_mem) {
+ ret = inf->share_video_mem(fbi->fb.screen_base,
+ fbi->screen_dma, pxafb_driver.driver.owner,
+ inf->extra_data);
+ if (ret)
+ return ret;
+ }
}
return fbi->map_cpu ? 0 : -ENOMEM;
@@ -1350,6 +1371,7 @@ static void pxafb_decode_mode_info(struct pxafb_info *fbi,
unsigned int num_modes)
{
unsigned int i, smemlen;
+ struct pxafb_mach_info *inf = fbi->dev->platform_data;
pxafb_setmode(&fbi->fb.var, &modes[0]);
@@ -1357,6 +1379,8 @@ static void pxafb_decode_mode_info(struct pxafb_info *fbi,
smemlen = modes[i].xres * modes[i].yres * modes[i].bpp / 8;
if (smemlen > fbi->fb.fix.smem_len)
fbi->fb.fix.smem_len = smemlen;
+ if (inf->custom_xfer_div)
+ fbi->fb.fix.smem_len /= inf->custom_xfer_div;
}
}
@@ -1761,10 +1785,12 @@ static int __devinit pxafb_probe(struct platform_device *dev)
}
/* Initialize video memory */
- ret = pxafb_map_video_memory(fbi);
- if (ret) {
+ ret = pxafb_map_video_memory(fbi, inf);
+ if (ret == -ENODEV) {
+ dev_err(&dev->dev, "Failed device binding: %d\n", ret);
+ goto failed_free_mem;
+ } else if (ret) {
dev_err(&dev->dev, "Failed to allocate video RAM: %d\n", ret);
- ret = -ENOMEM;
goto failed_free_io;
}
@@ -1836,6 +1862,8 @@ failed_free_cmap:
failed_free_irq:
free_irq(irq, fbi);
failed_free_mem:
+ if (inf->unshare_video_mem)
+ inf->unshare_video_mem(inf->extra_data);
dma_free_writecombine(&dev->dev, fbi->map_size,
fbi->map_cpu, fbi->map_dma);
failed_free_io:
@@ -1856,6 +1884,7 @@ static int __devexit pxafb_remove(struct platform_device *dev)
struct resource *r;
int irq;
struct fb_info *info;
+ struct pxafb_mach_info *inf;
if (!fbi)
return 0;
@@ -1872,6 +1901,9 @@ static int __devexit pxafb_remove(struct platform_device *dev)
irq = platform_get_irq(dev, 0);
free_irq(irq, fbi);
+ inf = dev->dev.platform_data;
+ if (inf->unshare_video_mem)
+ inf->unshare_video_mem(inf->extra_data);
dma_free_writecombine(&dev->dev, fbi->map_size,
fbi->map_cpu, fbi->map_dma);
diff --git a/include/asm-arm/arch-pxa/pxafb.h b/include/asm-arm/arch-pxa/pxafb.h
index daf018d..c73751e 100644
--- a/include/asm-arm/arch-pxa/pxafb.h
+++ b/include/asm-arm/arch-pxa/pxafb.h
@@ -139,9 +139,17 @@ struct pxafb_mach_info {
* All other bits in LCCR4 should be left alone.
*/
u_int lccr4;
+ unsigned int custom_xfer_div; /* divides the pixel transfer */
+ /* size of extra mem needed for secondary driver */
+ unsigned int extra_video_mem;
+ void *extra_data; /* extra data for secondary */
void (*pxafb_backlight_power)(int);
void (*pxafb_lcd_power)(int, struct fb_var_screeninfo *);
void (*smart_update)(struct fb_info *);
+ /* share_video_mem allows client drivers to get our framebuffer */
+ int (*share_video_mem)(char __iomem *, dma_addr_t, struct module *,
+ void *);
+ void (*unshare_video_mem)(void *);
};
void set_pxa_fb_info(struct pxafb_mach_info *hard_pxa_fb_info);
void set_pxa_fb_parent(struct device *parent_dev);
--
1.5.3.6
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply related [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 2/5] gumstix: conversion to MFP support and add bluetooth support
2008-07-20 6:10 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6 Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
@ 2008-07-20 6:10 ` Jaya Kumar
2008-07-21 2:13 ` eric miao
2008-07-20 6:10 ` [RFC 2.6.26-rc9 3/5] am200epd: convert to shared fb and use gpio api Jaya Kumar
` (2 subsequent siblings)
4 siblings, 1 reply; 18+ messages in thread
From: Jaya Kumar @ 2008-07-20 6:10 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
This patch converts gumstix over to the MFP configuration system and adds
bluetooth support.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
arch/arm/mach-pxa/gumstix.c | 94 +++++++++++++++++++++++++++++++++++--------
1 files changed, 77 insertions(+), 17 deletions(-)
diff --git a/arch/arm/mach-pxa/gumstix.c b/arch/arm/mach-pxa/gumstix.c
index bdf2397..06493ff 100644
--- a/arch/arm/mach-pxa/gumstix.c
+++ b/arch/arm/mach-pxa/gumstix.c
@@ -20,8 +20,12 @@
#include <linux/init.h>
#include <linux/platform_device.h>
#include <linux/interrupt.h>
+#include <linux/delay.h>
#include <linux/mtd/mtd.h>
#include <linux/mtd/partitions.h>
+#include <linux/gpio.h>
+#include <linux/err.h>
+#include <linux/clk.h>
#include <asm/setup.h>
#include <asm/memory.h>
@@ -40,7 +44,7 @@
#include <asm/arch/pxa-regs.h>
#include <asm/arch/pxa2xx-regs.h>
-#include <asm/arch/pxa2xx-gpio.h>
+#include <asm/arch/mfp-pxa25x.h>
#include "generic.h"
@@ -85,21 +89,8 @@ static struct platform_device *devices[] __initdata = {
};
#ifdef CONFIG_MMC_PXA
-static struct pxamci_platform_data gumstix_mci_platform_data;
-
-static int gumstix_mci_init(struct device *dev, irq_handler_t detect_int,
- void *data)
-{
- pxa_gpio_mode(GPIO6_MMCCLK_MD);
- pxa_gpio_mode(GPIO53_MMCCLK_MD);
- pxa_gpio_mode(GPIO8_MMCCS0_MD);
-
- return 0;
-}
-
static struct pxamci_platform_data gumstix_mci_platform_data = {
.ocr_mask = MMC_VDD_32_33|MMC_VDD_33_34,
- .init = gumstix_mci_init,
};
static void __init gumstix_mmc_init(void)
@@ -109,11 +100,11 @@ static void __init gumstix_mmc_init(void)
#else
static void __init gumstix_mmc_init(void)
{
- printk(KERN_INFO "Gumstix mmc disabled\n");
+ pr_debug("Gumstix mmc disabled\n");
}
#endif
-#ifdef CONFIG_USB_GADGET_PXA2XX
+#ifdef CONFIG_USB_GADGET_PXA25X
static struct pxa2xx_udc_mach_info gumstix_udc_info __initdata = {
.gpio_vbus = GPIO_GUMSTIX_USB_GPIOn,
.gpio_pullup = GPIO_GUMSTIX_USB_GPIOx,
@@ -126,12 +117,81 @@ static void __init gumstix_udc_init(void)
#else
static void gumstix_udc_init(void)
{
- printk(KERN_INFO "Gumstix udc is disabled\n");
+ pr_debug("Gumstix udc is disabled\n");
}
#endif
+#ifdef CONFIG_BT
+/* Normally, the bootloader would have enabled this 32kHz clock but many
+** boards still have u-boot 1.1.4 so we check if it has been turned on and
+** if not, we turn it on with a warning message. */
+static void gumstix_setup_bt_clock(void)
+{
+ int timeout = 500;
+
+ if (!(OSCC & OSCC_OOK))
+ pr_warning("32kHz clock was not on. Bootloader may need to "
+ "be updated\n");
+ else
+ return;
+
+ OSCC |= OSCC_OON;
+ do {
+ if (OSCC & OSCC_OOK)
+ break;
+ udelay(1);
+ } while (--timeout);
+ if (!timeout)
+ pr_err("Failed to start 32kHz clock\n");
+}
+
+static void __init gumstix_bluetooth_init(void)
+{
+ int err;
+
+ gumstix_setup_bt_clock();
+
+ err = gpio_direction_output(GPIO_GUMSTIX_BTRESET, 1);
+ if (err) {
+ pr_err("gumstix: can't reset bluetooth\n");
+ return;
+ }
+ gpio_set_value(GPIO_GUMSTIX_BTRESET, 0);
+ udelay(100);
+ gpio_set_value(GPIO_GUMSTIX_BTRESET, 1);
+}
+#else
+static void gumstix_bluetooth_init(void)
+{
+ pr_debug("Gumstix Bluetooth is disabled\n");
+}
+#endif
+
+static unsigned long gumstix_pin_config[] __initdata = {
+ GPIO12_32KHz,
+ /* BTUART */
+ GPIO42_HWUART_RXD,
+ GPIO43_HWUART_TXD,
+ GPIO44_HWUART_CTS,
+ GPIO45_HWUART_RTS,
+ /* MMC */
+ GPIO6_MMC_CLK,
+ GPIO53_MMC_CLK,
+ GPIO8_MMC_CS0,
+ /* these are used by AM200EPD */
+ GPIO51_GPIO,
+ GPIO49_GPIO,
+ GPIO48_GPIO,
+ GPIO32_GPIO,
+ GPIO17_GPIO,
+ GPIO16_GPIO,
+};
+
static void __init gumstix_init(void)
{
+ pxa2xx_mfp_config(ARRAY_AND_SIZE(gumstix_pin_config));
+
+ gumstix_bluetooth_init();
gumstix_udc_init();
gumstix_mmc_init();
(void) platform_add_devices(devices, ARRAY_SIZE(devices));
--
1.5.3.6
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply related [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 3/5] am200epd: convert to shared fb and use gpio api
2008-07-20 6:10 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6 Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 2/5] gumstix: conversion to MFP support and add bluetooth support Jaya Kumar
@ 2008-07-20 6:10 ` Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 5/5] metronomefb: changes to use separate framebuffer Jaya Kumar
4 siblings, 0 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-20 6:10 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
The original am200epd driver was designed with bad assumptions. It
manipulated GPSR/GPLR registers directly. It relied on direct access to the
pxa LCDC registers which have since conflicted with commit
ce4fb7b892a6d6c6a0f87366b26fd834d2923dd7 . This patch moves it into mach-pxa
and overhauls it to use pxafb's fb. It now uses the generic GPIO api.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
arch/arm/mach-pxa/Kconfig | 3 +
arch/arm/mach-pxa/Makefile | 1 +
arch/arm/mach-pxa/am200epd.c | 326 ++++++++++++++++++++++++++++++++++++++++++
drivers/video/Kconfig | 13 --
drivers/video/Makefile | 1 -
drivers/video/am200epd.c | 295 --------------------------------------
6 files changed, 330 insertions(+), 309 deletions(-)
create mode 100644 arch/arm/mach-pxa/am200epd.c
delete mode 100644 drivers/video/am200epd.c
diff --git a/arch/arm/mach-pxa/Kconfig b/arch/arm/mach-pxa/Kconfig
index 3e28521..945014e 100644
--- a/arch/arm/mach-pxa/Kconfig
+++ b/arch/arm/mach-pxa/Kconfig
@@ -243,6 +243,9 @@ config PCM990_DISPLAY_NONE
endchoice
+config MACH_AM200EPD
+ depends on MACH_GUMSTIX_F
+ bool "Enable AM200EPD board support"
config PXA_EZX
bool "Motorola EZX Platform"
diff --git a/arch/arm/mach-pxa/Makefile b/arch/arm/mach-pxa/Makefile
index 5220a5c..618fe96 100644
--- a/arch/arm/mach-pxa/Makefile
+++ b/arch/arm/mach-pxa/Makefile
@@ -21,6 +21,7 @@ obj-$(CONFIG_CPU_PXA320) += pxa320.o
# Specific board support
obj-$(CONFIG_ARCH_GUMSTIX) += gumstix.o
+obj-$(CONFIG_MACH_AM200EPD) += am200epd.o
obj-$(CONFIG_ARCH_LUBBOCK) += lubbock.o
obj-$(CONFIG_MACH_LOGICPD_PXA270) += lpd270.o
obj-$(CONFIG_MACH_MAINSTONE) += mainstone.o
diff --git a/arch/arm/mach-pxa/am200epd.c b/arch/arm/mach-pxa/am200epd.c
new file mode 100644
index 0000000..87e9fa8
--- /dev/null
+++ b/arch/arm/mach-pxa/am200epd.c
@@ -0,0 +1,326 @@
+/*
+ * am200epd.c -- Platform device for AM200 EPD kit
+ *
+ * Copyright (C) 2008, Jaya Kumar
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file COPYING in the main directory of this archive for
+ * more details.
+ *
+ * Layout is based on skeletonfb.c by James Simmons and Geert Uytterhoeven.
+ *
+ * This work was made possible by help and equipment support from E-Ink
+ * Corporation. http://support.eink.com/community
+ *
+ * This driver is written to be used with the Metronome display controller.
+ * on the AM200 EPD prototype kit/development kit with an E-Ink 800x600
+ * Vizplex EPD on a Gumstix board using the Lyre interface board.
+ *
+ */
+
+#define DEBUG 1
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/delay.h>
+#include <linux/interrupt.h>
+#include <linux/fb.h>
+#include <linux/init.h>
+#include <linux/platform_device.h>
+#include <linux/irq.h>
+#include <linux/gpio.h>
+
+#include <asm/arch/pxafb.h>
+
+#include <video/metronomefb.h>
+
+#include "generic.h"
+#include "devices.h"
+
+static unsigned int panel_type = 6;
+static struct platform_device *am200_device;
+static struct metronome_board am200_board;
+
+static struct pxafb_mode_info am200_fb_mode_9inch7 = {
+ .pixclock = 40000,
+ .xres = 1200,
+ .yres = 842,
+ .bpp = 16,
+ .hsync_len = 2,
+ .left_margin = 2,
+ .right_margin = 2,
+ .vsync_len = 1,
+ .upper_margin = 2,
+ .lower_margin = 25,
+ .sync = FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT,
+};
+
+static struct pxafb_mode_info am200_fb_mode_8inch = {
+ .pixclock = 40000,
+ .xres = 1088,
+ .yres = 791,
+ .bpp = 16,
+ .hsync_len = 28,
+ .left_margin = 8,
+ .right_margin = 30,
+ .vsync_len = 8,
+ .upper_margin = 10,
+ .lower_margin = 8,
+ .sync = FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT,
+};
+
+static struct pxafb_mode_info am200_fb_mode_6inch = {
+ .pixclock = 40189,
+ .xres = 832,
+ .yres = 622,
+ .bpp = 16,
+ .hsync_len = 28,
+ .left_margin = 34,
+ .right_margin = 34,
+ .vsync_len = 25,
+ .upper_margin = 0,
+ .lower_margin = 2,
+ .sync = FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT,
+};
+
+static struct pxafb_mach_info am200_fb_info = {
+ .modes = &am200_fb_mode_6inch,
+ .num_modes = 1,
+ .lcd_conn = LCD_TYPE_COLOR_TFT | LCD_PCLK_EDGE_FALL |
+ LCD_AC_BIAS_FREQ(24),
+ .custom_xfer_div = 2,
+};
+
+/* register offsets for gpio control */
+#define LED_GPIO_PIN 51
+#define STDBY_GPIO_PIN 48
+#define RST_GPIO_PIN 49
+#define RDY_GPIO_PIN 32
+#define ERR_GPIO_PIN 17
+#define PCBPWR_GPIO_PIN 16
+static int gpios[] = { LED_GPIO_PIN , STDBY_GPIO_PIN , RST_GPIO_PIN,
+ RDY_GPIO_PIN, ERR_GPIO_PIN, PCBPWR_GPIO_PIN };
+static char *gpio_names[] = { "LED" , "STDBY" , "RST", "RDY", "ERR", "PCBPWR" };
+
+static int am200_init_gpio_regs(struct metronomefb_par *par)
+{
+ int i;
+ int err;
+
+ for (i = 0; i < ARRAY_SIZE(gpios); i++) {
+ err = gpio_request(gpios[i], gpio_names[i]);
+ if (err) {
+ dev_err(&am200_device->dev, "failed requesting "
+ "gpio %s, err=%d\n", gpio_names[i], err);
+ goto err_req_gpio;
+ }
+ }
+
+ gpio_direction_output(LED_GPIO_PIN, 0);
+ gpio_direction_output(STDBY_GPIO_PIN, 0);
+ gpio_direction_output(RST_GPIO_PIN, 0);
+
+ gpio_direction_input(RDY_GPIO_PIN);
+ gpio_direction_input(ERR_GPIO_PIN);
+
+ gpio_direction_output(PCBPWR_GPIO_PIN, 0);
+
+ return 0;
+
+err_req_gpio:
+ while (i > 0)
+ gpio_free(gpios[i--]);
+
+ return err;
+}
+
+static void am200_cleanup(struct metronomefb_par *par)
+{
+ int i;
+
+ free_irq(IRQ_GPIO(RDY_GPIO_PIN), par->info);
+
+ for (i = 0; i < ARRAY_SIZE(gpios); i++)
+ gpio_free(gpios[i]);
+}
+
+static char __iomem *am200_metromem;
+static dma_addr_t am200_metromem_dma;
+static int am200_preshare_video_mem(char __iomem *video_mem, dma_addr_t dma,
+ struct module *fbmaster, void *data)
+{
+
+ /* try to refcount the caller since we are the consumer after this */
+ if (!try_module_get(fbmaster))
+ return -ENODEV;
+
+ dev_dbg(&am200_device->dev, "mod_get %p\n", fbmaster);
+ am200_board.fbmaster = fbmaster;
+ am200_metromem = video_mem;
+ am200_metromem_dma = dma;
+
+ return 0;
+}
+
+static void am200_unshare_video_mem(void *data)
+{
+ struct metronomefb_par *par = data;
+
+ dev_dbg(&am200_device->dev, "ENTER %s\n", __func__);
+ par->metromem = NULL;
+ par->metromem_dma = 0;
+ dev_dbg(&am200_device->dev, "mod_put %p\n", am200_board.fbmaster);
+ module_put(am200_board.fbmaster);
+}
+
+/* this gets called as part of our init. these steps must be done now so
+ * that we can use set_pxa_fb_info */
+static void __init am200_presetup_fb(void)
+{
+ int fw;
+ int wfm_size;
+ int padding_size;
+
+ switch (panel_type) {
+ case 6:
+ am200_fb_info.modes = &am200_fb_mode_6inch;
+ break;
+ case 8:
+ am200_fb_info.modes = &am200_fb_mode_8inch;
+ break;
+ case 97:
+ am200_fb_info.modes = &am200_fb_mode_9inch7;
+ break;
+ default:
+ dev_err(&am200_device->dev, "invalid panel_type selection,"
+ " setting to 6\n");
+ am200_fb_info.modes = &am200_fb_mode_6inch;
+ break;
+ }
+
+ fw = am200_fb_info.modes->xres;
+ wfm_size = ((16*1024 + 2 + fw - 1) / fw) * fw;
+ padding_size = 4 * fw;
+ am200_fb_info.extra_video_mem = fw + wfm_size + padding_size;
+ am200_fb_info.share_video_mem = am200_preshare_video_mem;
+ am200_fb_info.unshare_video_mem = NULL;
+
+ set_pxa_fb_info(&am200_fb_info);
+
+}
+
+/* this gets called by metronomefb as part of its init, in our case, we
+ * have already completed initial framebuffer init in presetup_fb so we
+ * can just assign the parameters for completeness */
+static int am200_setup_fb(struct metronomefb_par *par)
+{
+
+ am200_fb_info.extra_video_mem = par->extra_size;
+ am200_fb_info.extra_data = (void *) par;
+ am200_fb_info.unshare_video_mem = am200_unshare_video_mem;
+
+ par->metromem = (unsigned char __force *) am200_metromem;
+ par->metromem_dma = am200_metromem_dma;
+
+ return 0;
+}
+
+static int am200_get_panel_type(void)
+{
+ return panel_type;
+}
+
+static irqreturn_t am200_handle_irq(int irq, void *dev_id)
+{
+ struct fb_info *info = dev_id;
+ struct metronomefb_par *par = info->par;
+
+ wake_up_interruptible(&par->waitq);
+ return IRQ_HANDLED;
+}
+
+static int am200_setup_irq(struct fb_info *info)
+{
+ int ret;
+
+ ret = request_irq(IRQ_GPIO(RDY_GPIO_PIN), am200_handle_irq,
+ IRQF_DISABLED|IRQF_TRIGGER_FALLING,
+ "AM200", info);
+ if (ret)
+ dev_err(&am200_device->dev, "request_irq failed: %d\n", ret);
+
+ return ret;
+}
+
+static void am200_set_rst(struct metronomefb_par *par, int state)
+{
+ gpio_set_value(RST_GPIO_PIN, state);
+}
+
+static void am200_set_stdby(struct metronomefb_par *par, int state)
+{
+ gpio_set_value(STDBY_GPIO_PIN, state);
+}
+
+static int am200_wait_event(struct metronomefb_par *par)
+{
+ return wait_event_timeout(par->waitq, gpio_get_value(RDY_GPIO_PIN), HZ);
+}
+
+static int am200_wait_event_intr(struct metronomefb_par *par)
+{
+ int ret;
+
+ ret = wait_event_interruptible_timeout(par->waitq,
+ gpio_get_value(RDY_GPIO_PIN), HZ);
+ return ret;
+}
+
+static struct metronome_board am200_board = {
+ .owner = THIS_MODULE,
+ .setup_irq = am200_setup_irq,
+ .setup_io = am200_init_gpio_regs,
+ .setup_fb = am200_setup_fb,
+ .set_rst = am200_set_rst,
+ .set_stdby = am200_set_stdby,
+ .met_wait_event = am200_wait_event,
+ .met_wait_event_intr = am200_wait_event_intr,
+ .get_panel_type = am200_get_panel_type,
+ .cleanup = am200_cleanup,
+};
+
+static int __init am200_init(void)
+{
+ int ret;
+
+ /* request our platform independent driver */
+ request_module("metronomefb");
+
+ am200_device = platform_device_alloc("metronomefb", -1);
+ if (!am200_device)
+ return -ENOMEM;
+
+ platform_device_add_data(am200_device, &am200_board,
+ sizeof(am200_board));
+
+ /* this _add binds metronomefb to am200. metronomefb refcounts am200 */
+ ret = platform_device_add(am200_device);
+
+ if (ret)
+ platform_device_put(am200_device);
+
+ am200_presetup_fb();
+
+ return ret;
+}
+
+module_param(panel_type, uint, 0);
+MODULE_PARM_DESC(panel_type, "Select the panel type: 6, 8, 97");
+
+module_init(am200_init);
+
+MODULE_DESCRIPTION("board driver for am200 metronome epd kit");
+MODULE_AUTHOR("Jaya Kumar");
+MODULE_LICENSE("GPL");
diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig
index e0c5f96..752907d 100644
--- a/drivers/video/Kconfig
+++ b/drivers/video/Kconfig
@@ -1938,19 +1938,6 @@ config FB_XILINX
framebuffer. ML300 carries a 640*480 LCD display on the board,
ML403 uses a standard DB15 VGA connector.
-config FB_AM200EPD
- tristate "AM-200 E-Ink EPD devkit support"
- depends on FB && ARCH_PXA && MMU
- select FB_SYS_FILLRECT
- select FB_SYS_COPYAREA
- select FB_SYS_IMAGEBLIT
- select FB_SYS_FOPS
- select FB_DEFERRED_IO
- select FB_METRONOME
- help
- This enables support for the Metronome display controller used on
- the E-Ink AM-200 EPD devkit.
-
config FB_VIRTUAL
tristate "Virtual Frame Buffer support (ONLY FOR TESTING!)"
depends on FB
diff --git a/drivers/video/Makefile b/drivers/video/Makefile
index 04bca35..80d5842 100644
--- a/drivers/video/Makefile
+++ b/drivers/video/Makefile
@@ -29,7 +29,6 @@ obj-$(CONFIG_FB_DEFERRED_IO) += fb_defio.o
# Hardware specific drivers go first
obj-$(CONFIG_FB_AMIGA) += amifb.o c2p.o
-obj-$(CONFIG_FB_AM200EPD) += am200epd.o
obj-$(CONFIG_FB_ARC) += arcfb.o
obj-$(CONFIG_FB_CLPS711X) += clps711xfb.o
obj-$(CONFIG_FB_CYBER2000) += cyber2000fb.o
diff --git a/drivers/video/am200epd.c b/drivers/video/am200epd.c
deleted file mode 100644
index 51e26c1..0000000
--- a/drivers/video/am200epd.c
+++ /dev/null
@@ -1,295 +0,0 @@
-/*
- * linux/drivers/video/am200epd.c -- Platform device for AM200 EPD kit
- *
- * Copyright (C) 2008, Jaya Kumar
- *
- * This file is subject to the terms and conditions of the GNU General Public
- * License. See the file COPYING in the main directory of this archive for
- * more details.
- *
- * Layout is based on skeletonfb.c by James Simmons and Geert Uytterhoeven.
- *
- * This work was made possible by help and equipment support from E-Ink
- * Corporation. http://support.eink.com/community
- *
- * This driver is written to be used with the Metronome display controller.
- * on the AM200 EPD prototype kit/development kit with an E-Ink 800x600
- * Vizplex EPD on a Gumstix board using the Lyre interface board.
- *
- */
-
-#include <linux/module.h>
-#include <linux/kernel.h>
-#include <linux/errno.h>
-#include <linux/string.h>
-#include <linux/delay.h>
-#include <linux/interrupt.h>
-#include <linux/fb.h>
-#include <linux/init.h>
-#include <linux/platform_device.h>
-#include <linux/list.h>
-#include <linux/uaccess.h>
-#include <linux/irq.h>
-
-#include <video/metronomefb.h>
-
-#include <asm/arch/pxa-regs.h>
-
-/* register offsets for gpio control */
-#define LED_GPIO_PIN 51
-#define STDBY_GPIO_PIN 48
-#define RST_GPIO_PIN 49
-#define RDY_GPIO_PIN 32
-#define ERR_GPIO_PIN 17
-#define PCBPWR_GPIO_PIN 16
-
-#define AF_SEL_GPIO_N 0x3
-#define GAFR0_U_OFFSET(pin) ((pin - 16) * 2)
-#define GAFR1_L_OFFSET(pin) ((pin - 32) * 2)
-#define GAFR1_U_OFFSET(pin) ((pin - 48) * 2)
-#define GPDR1_OFFSET(pin) (pin - 32)
-#define GPCR1_OFFSET(pin) (pin - 32)
-#define GPSR1_OFFSET(pin) (pin - 32)
-#define GPCR0_OFFSET(pin) (pin)
-#define GPSR0_OFFSET(pin) (pin)
-
-static void am200_set_gpio_output(int pin, int val)
-{
- u8 index;
-
- index = pin >> 4;
-
- switch (index) {
- case 1:
- if (val)
- GPSR0 |= (1 << GPSR0_OFFSET(pin));
- else
- GPCR0 |= (1 << GPCR0_OFFSET(pin));
- break;
- case 2:
- break;
- case 3:
- if (val)
- GPSR1 |= (1 << GPSR1_OFFSET(pin));
- else
- GPCR1 |= (1 << GPCR1_OFFSET(pin));
- break;
- default:
- printk(KERN_ERR "unimplemented\n");
- }
-}
-
-static void __devinit am200_init_gpio_pin(int pin, int dir)
-{
- u8 index;
- /* dir 0 is output, 1 is input
- - do 2 things here:
- - set gpio alternate function to standard gpio
- - set gpio direction to input or output */
-
- index = pin >> 4;
- switch (index) {
- case 1:
- GAFR0_U &= ~(AF_SEL_GPIO_N << GAFR0_U_OFFSET(pin));
-
- if (dir)
- GPDR0 &= ~(1 << pin);
- else
- GPDR0 |= (1 << pin);
- break;
- case 2:
- GAFR1_L &= ~(AF_SEL_GPIO_N << GAFR1_L_OFFSET(pin));
-
- if (dir)
- GPDR1 &= ~(1 << GPDR1_OFFSET(pin));
- else
- GPDR1 |= (1 << GPDR1_OFFSET(pin));
- break;
- case 3:
- GAFR1_U &= ~(AF_SEL_GPIO_N << GAFR1_U_OFFSET(pin));
-
- if (dir)
- GPDR1 &= ~(1 << GPDR1_OFFSET(pin));
- else
- GPDR1 |= (1 << GPDR1_OFFSET(pin));
- break;
- default:
- printk(KERN_ERR "unimplemented\n");
- }
-}
-
-static void am200_init_gpio_regs(struct metronomefb_par *par)
-{
- am200_init_gpio_pin(LED_GPIO_PIN, 0);
- am200_set_gpio_output(LED_GPIO_PIN, 0);
-
- am200_init_gpio_pin(STDBY_GPIO_PIN, 0);
- am200_set_gpio_output(STDBY_GPIO_PIN, 0);
-
- am200_init_gpio_pin(RST_GPIO_PIN, 0);
- am200_set_gpio_output(RST_GPIO_PIN, 0);
-
- am200_init_gpio_pin(RDY_GPIO_PIN, 1);
-
- am200_init_gpio_pin(ERR_GPIO_PIN, 1);
-
- am200_init_gpio_pin(PCBPWR_GPIO_PIN, 0);
- am200_set_gpio_output(PCBPWR_GPIO_PIN, 0);
-}
-
-static void am200_disable_lcd_controller(struct metronomefb_par *par)
-{
- LCSR = 0xffffffff; /* Clear LCD Status Register */
- LCCR0 |= LCCR0_DIS; /* Disable LCD Controller */
-
- /* we reset and just wait for things to settle */
- msleep(200);
-}
-
-static void am200_enable_lcd_controller(struct metronomefb_par *par)
-{
- LCSR = 0xffffffff;
- FDADR0 = par->metromem_desc_dma;
- LCCR0 |= LCCR0_ENB;
-}
-
-static void am200_init_lcdc_regs(struct metronomefb_par *par)
-{
- /* here we do:
- - disable the lcd controller
- - setup lcd control registers
- - setup dma descriptor
- - reenable lcd controller
- */
-
- /* disable the lcd controller */
- am200_disable_lcd_controller(par);
-
- /* setup lcd control registers */
- LCCR0 = LCCR0_LDM | LCCR0_SFM | LCCR0_IUM | LCCR0_EFM | LCCR0_PAS
- | LCCR0_QDM | LCCR0_BM | LCCR0_OUM;
-
- LCCR1 = (par->info->var.xres/2 - 1) /* pixels per line */
- | (27 << 10) /* hsync pulse width - 1 */
- | (33 << 16) /* eol pixel count */
- | (33 << 24); /* bol pixel count */
-
- LCCR2 = (par->info->var.yres - 1) /* lines per panel */
- | (24 << 10) /* vsync pulse width - 1 */
- | (2 << 16) /* eof pixel count */
- | (0 << 24); /* bof pixel count */
-
- LCCR3 = 2 /* pixel clock divisor */
- | (24 << 8) /* AC Bias pin freq */
- | LCCR3_16BPP /* BPP */
- | LCCR3_PCP; /* PCP falling edge */
-
-}
-
-static void am200_post_dma_setup(struct metronomefb_par *par)
-{
- par->metromem_desc->mFDADR0 = par->metromem_desc_dma;
- par->metromem_desc->mFSADR0 = par->metromem_dma;
- par->metromem_desc->mFIDR0 = 0;
- par->metromem_desc->mLDCMD0 = par->info->var.xres
- * par->info->var.yres;
- am200_enable_lcd_controller(par);
-}
-
-static void am200_free_irq(struct fb_info *info)
-{
- free_irq(IRQ_GPIO(RDY_GPIO_PIN), info);
-}
-
-static irqreturn_t am200_handle_irq(int irq, void *dev_id)
-{
- struct fb_info *info = dev_id;
- struct metronomefb_par *par = info->par;
-
- wake_up_interruptible(&par->waitq);
- return IRQ_HANDLED;
-}
-
-static int am200_setup_irq(struct fb_info *info)
-{
- int retval;
-
- retval = request_irq(IRQ_GPIO(RDY_GPIO_PIN), am200_handle_irq,
- IRQF_DISABLED, "AM200", info);
- if (retval) {
- printk(KERN_ERR "am200epd: request_irq failed: %d\n", retval);
- return retval;
- }
-
- return set_irq_type(IRQ_GPIO(RDY_GPIO_PIN), IRQT_FALLING);
-}
-
-static void am200_set_rst(struct metronomefb_par *par, int state)
-{
- am200_set_gpio_output(RST_GPIO_PIN, state);
-}
-
-static void am200_set_stdby(struct metronomefb_par *par, int state)
-{
- am200_set_gpio_output(STDBY_GPIO_PIN, state);
-}
-
-static int am200_wait_event(struct metronomefb_par *par)
-{
- return wait_event_timeout(par->waitq, (GPLR1 & 0x01), HZ);
-}
-
-static int am200_wait_event_intr(struct metronomefb_par *par)
-{
- return wait_event_interruptible_timeout(par->waitq, (GPLR1 & 0x01), HZ);
-}
-
-static struct metronome_board am200_board = {
- .owner = THIS_MODULE,
- .free_irq = am200_free_irq,
- .setup_irq = am200_setup_irq,
- .init_gpio_regs = am200_init_gpio_regs,
- .init_lcdc_regs = am200_init_lcdc_regs,
- .post_dma_setup = am200_post_dma_setup,
- .set_rst = am200_set_rst,
- .set_stdby = am200_set_stdby,
- .met_wait_event = am200_wait_event,
- .met_wait_event_intr = am200_wait_event_intr,
-};
-
-static struct platform_device *am200_device;
-
-static int __init am200_init(void)
-{
- int ret;
-
- /* request our platform independent driver */
- request_module("metronomefb");
-
- am200_device = platform_device_alloc("metronomefb", -1);
- if (!am200_device)
- return -ENOMEM;
-
- platform_device_add_data(am200_device, &am200_board,
- sizeof(am200_board));
-
- /* this _add binds metronomefb to am200. metronomefb refcounts am200 */
- ret = platform_device_add(am200_device);
-
- if (ret)
- platform_device_put(am200_device);
-
- return ret;
-}
-
-static void __exit am200_exit(void)
-{
- platform_device_unregister(am200_device);
-}
-
-module_init(am200_init);
-module_exit(am200_exit);
-
-MODULE_DESCRIPTION("board driver for am200 metronome epd kit");
-MODULE_AUTHOR("Jaya Kumar");
-MODULE_LICENSE("GPL");
--
1.5.3.6
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply related [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages
2008-07-20 6:10 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6 Jaya Kumar
` (2 preceding siblings ...)
2008-07-20 6:10 ` [RFC 2.6.26-rc9 3/5] am200epd: convert to shared fb and use gpio api Jaya Kumar
@ 2008-07-20 6:10 ` Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 5/5] metronomefb: changes to use separate framebuffer Jaya Kumar
4 siblings, 0 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-20 6:10 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
This patch converts the printk messages in metronomefb to dev_dbg/err type
messages.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
drivers/video/metronomefb.c | 49 +++++++++++++++++++-----------------------
1 files changed, 22 insertions(+), 27 deletions(-)
diff --git a/drivers/video/metronomefb.c b/drivers/video/metronomefb.c
index cc4c038..8ccd113 100644
--- a/drivers/video/metronomefb.c
+++ b/drivers/video/metronomefb.c
@@ -18,6 +18,8 @@
* is provided as am200epd.c
*
*/
+#define DEBUG 1
+
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
@@ -40,15 +42,6 @@
#include <asm/unaligned.h>
-
-#define DEBUG 1
-#ifdef DEBUG
-#define DPRINTK(f, a...) printk(KERN_DEBUG "%s: " f, __func__ , ## a)
-#else
-#define DPRINTK(f, a...)
-#endif
-
-
/* Display specific information */
#define DPY_W 832
#define DPY_H 622
@@ -135,8 +128,8 @@ static u16 calc_img_cksum(u16 *start, int length)
/* here we decode the incoming waveform file and populate metromem */
#define EXP_WFORM_SIZE 47001
-static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
- u8 *frame_count)
+static int __devinit load_waveform(u8 *mem, size_t size, int m, int t,
+ struct metronomefb_par *par)
{
int tta;
int wmta;
@@ -148,9 +141,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
int wfm_idx, owfm_idx;
int mem_idx = 0;
struct waveform_hdr *wfm_hdr;
+ u8 *metromem = par->metromem_wfm;
+ struct device *dev = par->info->dev;
if (size != EXP_WFORM_SIZE) {
- printk(KERN_ERR "Error: unexpected size %d != %d\n", size,
+ dev_err(dev, "Error: unexpected size %d != %d\n", size,
EXP_WFORM_SIZE);
return -EINVAL;
}
@@ -158,16 +153,16 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
wfm_hdr = (struct waveform_hdr *) mem;
if (wfm_hdr->fvsn != 1) {
- printk(KERN_ERR "Error: bad fvsn %x\n", wfm_hdr->fvsn);
+ dev_err(dev, "Error: bad fvsn %x\n", wfm_hdr->fvsn);
return -EINVAL;
}
if (wfm_hdr->luts != 0) {
- printk(KERN_ERR "Error: bad luts %x\n", wfm_hdr->luts);
+ dev_err(dev, "Error: bad luts %x\n", wfm_hdr->luts);
return -EINVAL;
}
cksum = calc_cksum(32, 47, mem);
if (cksum != wfm_hdr->wfm_cs) {
- printk(KERN_ERR "Error: bad cksum %x != %x\n", cksum,
+ dev_err(dev, "Error: bad cksum %x != %x\n", cksum,
wfm_hdr->wfm_cs);
return -EINVAL;
}
@@ -175,7 +170,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
wfm_hdr->trc += 1;
for (i = 0; i < 5; i++) {
if (*(wfm_hdr->stuff2a + i) != 0) {
- printk(KERN_ERR "Error: unexpected value in padding\n");
+ dev_err(dev, "Error: unexpected value in padding\n");
return -EINVAL;
}
}
@@ -200,7 +195,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(sizeof(*wfm_hdr), cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad temperature range table cksum"
+ dev_err(dev, "Error: bad temperature range table cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -212,7 +207,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad mode table address cksum"
+ dev_err(dev, "Error: bad mode table address cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -224,7 +219,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad temperature table address cksum"
+ dev_err(dev, "Error: bad temperature table address cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -259,11 +254,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(owfm_idx, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad waveform data cksum"
+ dev_err(dev, "Error: bad waveform data cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
- *frame_count = (mem_idx/64);
+ par->frame_count = (mem_idx/64);
return 0;
}
@@ -662,15 +657,15 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
b) process waveform and decode into metromem */
retval = request_firmware(&fw_entry, "metronome.wbf", &dev->dev);
if (retval < 0) {
- printk(KERN_ERR "metronomefb: couldn't get waveform\n");
+ dev_err(&dev->dev, "Failed to get waveform\n");
goto err_dma_free;
}
- retval = load_waveform((u8 *) fw_entry->data, fw_entry->size,
- par->metromem_wfm, 3, 31, &par->frame_count);
+ retval = load_waveform((u8 *) fw_entry->data, fw_entry->size, 3, 31,
+ par);
release_firmware(fw_entry);
if (retval < 0) {
- printk(KERN_ERR "metronomefb: couldn't process waveform\n");
+ dev_err(&dev->dev, "Failed processing waveform\n");
goto err_dma_free;
}
@@ -688,7 +683,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
retval = fb_alloc_cmap(&info->cmap, 8, 0);
if (retval < 0) {
- printk(KERN_ERR "Failed to allocate colormap\n");
+ dev_err(&dev->dev, "Failed to allocate colormap\n");
goto err_fb_rel;
}
@@ -704,7 +699,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
platform_set_drvdata(dev, info);
- printk(KERN_INFO
+ dev_dbg(&dev->dev,
"fb%d: Metronome frame buffer device, using %dK of video"
" memory\n", info->node, videomemorysize >> 10);
--
1.5.3.6
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply related [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 5/5] metronomefb: changes to use separate framebuffer
2008-07-20 6:10 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6 Jaya Kumar
` (3 preceding siblings ...)
2008-07-20 6:10 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
@ 2008-07-20 6:10 ` Jaya Kumar
4 siblings, 0 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-20 6:10 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
These changes are used in order to support the use of a separate
framebuffer provided by the platform device driver. Other changes
are cleanup to error handling and order of release.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
drivers/video/Kconfig | 18 +++-
drivers/video/metronomefb.c | 225 +++++++++++++++++++++++++------------------
include/video/metronomefb.h | 22 ++---
3 files changed, 151 insertions(+), 114 deletions(-)
diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig
index 752907d..dda770c 100644
--- a/drivers/video/Kconfig
+++ b/drivers/video/Kconfig
@@ -172,11 +172,6 @@ config FB_DEFERRED_IO
bool
depends on FB
-config FB_METRONOME
- tristate
- depends on FB
- depends on FB_DEFERRED_IO
-
config FB_HECUBA
tristate
depends on FB
@@ -1975,6 +1970,19 @@ config XEN_FBDEV_FRONTEND
frame buffer driver. It communicates with a back-end
in another domain.
+config FB_METRONOME
+ tristate "E-Ink Metronome/8track controller support"
+ depends on FB
+ select FB_SYS_FILLRECT
+ select FB_SYS_COPYAREA
+ select FB_SYS_IMAGEBLIT
+ select FB_SYS_FOPS
+ select FB_DEFERRED_IO
+ help
+ This driver implements support for the E-Ink Metronome
+ controller. The pre-release name for this device was 8track
+ and could also have been called by some vendors as PVI-nnnn.
+
source "drivers/video/omap/Kconfig"
source "drivers/video/backlight/Kconfig"
diff --git a/drivers/video/metronomefb.c b/drivers/video/metronomefb.c
index 8ccd113..471b0c1 100644
--- a/drivers/video/metronomefb.c
+++ b/drivers/video/metronomefb.c
@@ -46,16 +46,59 @@
#define DPY_W 832
#define DPY_H 622
+static int user_wfm_size;
+
/* frame differs from image. frame includes non-visible pixels */
struct epd_frame {
int fw; /* frame width */
int fh; /* frame height */
+ u16 config[4];
+ int wfm_size;
};
static struct epd_frame epd_frame_table[] = {
{
- .fw = 832,
- .fh = 622
+ .fw = 832,
+ .fh = 622,
+ .config = {
+ 15 /* sdlew */
+ | 2 << 8 /* sdosz */
+ | 0 << 11 /* sdor */
+ | 0 << 12 /* sdces */
+ | 0 << 15, /* sdcer */
+ 42 /* gdspl */
+ | 1 << 8 /* gdr1 */
+ | 1 << 9 /* sdshr */
+ | 0 << 15, /* gdspp */
+ 18 /* gdspw */
+ | 0 << 15, /* dispc */
+ 599 /* vdlc */
+ | 0 << 11 /* dsi */
+ | 0 << 12, /* dsic */
+ },
+ .wfm_size = 47001,
+ },
+ {
+ .fw = 1088,
+ .fh = 791,
+ .config = {
+ 0x0104,
+ 0x031f,
+ 0x0088,
+ 0x02ff,
+ },
+ .wfm_size = 46770,
+ },
+ {
+ .fw = 1200,
+ .fh = 842,
+ .config = {
+ 0x0101,
+ 0x030e,
+ 0x0012,
+ 0x0280,
+ },
+ .wfm_size = 46770,
},
};
@@ -127,7 +170,6 @@ static u16 calc_img_cksum(u16 *start, int length)
}
/* here we decode the incoming waveform file and populate metromem */
-#define EXP_WFORM_SIZE 47001
static int __devinit load_waveform(u8 *mem, size_t size, int m, int t,
struct metronomefb_par *par)
{
@@ -144,9 +186,12 @@ static int __devinit load_waveform(u8 *mem, size_t size, int m, int t,
u8 *metromem = par->metromem_wfm;
struct device *dev = par->info->dev;
- if (size != EXP_WFORM_SIZE) {
+ if (user_wfm_size)
+ epd_frame_table[par->dt].wfm_size = user_wfm_size;
+
+ if (size != epd_frame_table[par->dt].wfm_size) {
dev_err(dev, "Error: unexpected size %d != %d\n", size,
- EXP_WFORM_SIZE);
+ epd_frame_table[par->dt].wfm_size);
return -EINVAL;
}
@@ -330,44 +375,17 @@ static int __devinit metronome_powerup_cmd(struct metronomefb_par *par)
static int __devinit metronome_config_cmd(struct metronomefb_par *par)
{
- int i;
- u16 cs;
-
/* setup config command
we can't immediately set the opcode since the controller
- will try parse the command before we've set it all up
- so we just set cs here and set the opcode at the end */
-
- cs = 0xCC10;
-
- /* set the 12 args ( 8 bytes ) for config. see spec for meanings */
- i = 0;
- par->metromem_cmd->args[i] = 15 /* sdlew */
- | 2 << 8 /* sdosz */
- | 0 << 11 /* sdor */
- | 0 << 12 /* sdces */
- | 0 << 15; /* sdcer */
- cs += par->metromem_cmd->args[i++];
-
- par->metromem_cmd->args[i] = 42 /* gdspl */
- | 1 << 8 /* gdr1 */
- | 1 << 9 /* sdshr */
- | 0 << 15; /* gdspp */
- cs += par->metromem_cmd->args[i++];
-
- par->metromem_cmd->args[i] = 18 /* gdspw */
- | 0 << 15; /* dispc */
- cs += par->metromem_cmd->args[i++];
-
- par->metromem_cmd->args[i] = 599 /* vdlc */
- | 0 << 11 /* dsi */
- | 0 << 12; /* dsic */
- cs += par->metromem_cmd->args[i++];
+ will try parse the command before we've set it all up */
+ memcpy(par->metromem_cmd->args, epd_frame_table[par->dt].config,
+ sizeof(epd_frame_table[par->dt].config));
/* the rest are 0 */
- memset((u8 *) (par->metromem_cmd->args + i), 0, (32-i)*2);
+ memset((u8 *) (par->metromem_cmd->args + 4), 0, (32-4)*2);
- par->metromem_cmd->csum = cs;
+ par->metromem_cmd->csum = 0xCC10;
+ par->metromem_cmd->csum += calc_img_cksum(par->metromem_cmd->args, 4);
par->metromem_cmd->opcode = 0xCC10; /* config cmd */
return par->board->met_wait_event(par);
@@ -403,12 +421,9 @@ static int __devinit metronome_init_regs(struct metronomefb_par *par)
{
int res;
- par->board->init_gpio_regs(par);
-
- par->board->init_lcdc_regs(par);
-
- /* now that lcd is setup, setup dma descriptor */
- par->board->post_dma_setup(par);
+ res = par->board->setup_io(par);
+ if (res)
+ return res;
res = metronome_powerup_cmd(par);
if (res)
@@ -425,16 +440,16 @@ static int __devinit metronome_init_regs(struct metronomefb_par *par)
static void metronomefb_dpy_update(struct metronomefb_par *par)
{
+ int fbsize;
u16 cksum;
unsigned char *buf = (unsigned char __force *)par->info->screen_base;
+ fbsize = par->info->fix.smem_len;
/* copy from vm to metromem */
- memcpy(par->metromem_img, buf, DPY_W*DPY_H);
+ memcpy(par->metromem_img, buf, fbsize);
- cksum = calc_img_cksum((u16 *) par->metromem_img,
- (epd_frame_table[0].fw * DPY_H)/2);
- *((u16 *)(par->metromem_img) +
- (epd_frame_table[0].fw * DPY_H)/2) = cksum;
+ cksum = calc_img_cksum((u16 *) par->metromem_img, fbsize/2);
+ *((u16 *)(par->metromem_img) + fbsize/2) = cksum;
metronome_display_cmd(par);
}
@@ -569,8 +584,11 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
unsigned char *videomemory;
struct metronomefb_par *par;
const struct firmware *fw_entry;
- int cmd_size, wfm_size, img_size, padding_size, totalsize;
+ int cmd_size, wfm_size, padding_size;
int i;
+ int panel_type;
+ int fw, fh;
+ int epd_dt_index;
/* pick up board specific routines */
board = dev->dev.platform_data;
@@ -581,39 +599,65 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
if (!try_module_get(board->owner))
return -ENODEV;
+ info = framebuffer_alloc(sizeof(struct metronomefb_par), &dev->dev);
+ if (!info)
+ goto err;
+
/* we have two blocks of memory.
info->screen_base which is vm, and is the fb used by apps.
par->metromem which is physically contiguous memory and
contains the display controller commands, waveform,
processed image data and padding. this is the data pulled
- by the device's LCD controller and pushed to Metronome */
-
- videomemorysize = (DPY_W*DPY_H);
+ by the device's LCD controller and pushed to Metronome.
+ the metromem memory is allocated by the board driver and
+ is provided to us */
+
+ panel_type = board->get_panel_type();
+ switch (panel_type) {
+ case 6:
+ epd_dt_index = 0;
+ break;
+ case 8:
+ epd_dt_index = 1;
+ break;
+ case 97:
+ epd_dt_index = 2;
+ break;
+ default:
+ dev_err(&dev->dev, "Unexpected panel type. Defaulting to 6\n");
+ epd_dt_index = 0;
+ break;
+ }
+ fw = epd_frame_table[epd_dt_index].fw;
+ fh = epd_frame_table[epd_dt_index].fh;
+ videomemorysize = fw * fh;
videomemory = vmalloc(videomemorysize);
if (!videomemory)
- return -ENOMEM;
+ goto err_fb_rel;
memset(videomemory, 0, videomemorysize);
- info = framebuffer_alloc(sizeof(struct metronomefb_par), &dev->dev);
- if (!info)
- goto err_vfree;
-
info->screen_base = (char __force __iomem *)videomemory;
info->fbops = &metronomefb_ops;
+ metronomefb_fix.line_length = fw;
+ metronomefb_var.xres = fw;
+ metronomefb_var.yres = fh;
+ metronomefb_var.xres_virtual = fw;
+ metronomefb_var.yres_virtual = fh;
info->var = metronomefb_var;
info->fix = metronomefb_fix;
info->fix.smem_len = videomemorysize;
par = info->par;
par->info = info;
par->board = board;
+ par->dt = epd_dt_index;
init_waitqueue_head(&par->waitq);
/* this table caches per page csum values. */
par->csum_table = vmalloc(videomemorysize/PAGE_SIZE);
if (!par->csum_table)
- goto err_csum_table;
+ goto err_vfree;
/* the metromem buffer is divided as follows:
command | CRC | padding
@@ -623,34 +667,26 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
eg: IW=832 IH=622 WS=128
*/
- cmd_size = 1 * epd_frame_table[0].fw;
- wfm_size = ((16*1024 + 2 + epd_frame_table[0].fw - 1)
- / epd_frame_table[0].fw) * epd_frame_table[0].fw;
- img_size = epd_frame_table[0].fh * epd_frame_table[0].fw;
- padding_size = 4 * epd_frame_table[0].fw;
- totalsize = cmd_size + wfm_size + img_size + padding_size;
- par->metromemsize = PAGE_ALIGN(totalsize + 256);
- DPRINTK("desired memory size = %d\n", par->metromemsize);
- dev->dev.coherent_dma_mask = 0xffffffffull;
- par->metromem = dma_alloc_writecombine(&dev->dev, par->metromemsize,
- &par->metromem_dma, GFP_KERNEL);
+ cmd_size = 1 * fw;
+ wfm_size = ((16*1024 + 2 + fw - 1) / fw) * fw;
+ padding_size = 4 * fw;
+ par->extra_size = cmd_size + wfm_size + padding_size;
+ retval = par->board->setup_fb(par);
+ if (retval) {
+ dev_err(&dev->dev, "Failed to setup fb\n");
+ goto err_csum_table;
+ }
+ /* after this point we should have a framebuffer */
if (!par->metromem) {
- printk(KERN_ERR
- "metronomefb: unable to allocate dma buffer\n");
- goto err_vfree;
+ retval = -EINVAL;
+ goto err_csum_table;
}
info->fix.smem_start = par->metromem_dma;
par->metromem_cmd = (struct metromem_cmd *) par->metromem;
par->metromem_wfm = par->metromem + cmd_size;
par->metromem_img = par->metromem + cmd_size + wfm_size;
- par->metromem_img_csum = (u16 *) (par->metromem_img +
- (epd_frame_table[0].fw * DPY_H));
- DPRINTK("img offset=0x%x\n", cmd_size + wfm_size);
- par->metromem_desc = (struct metromem_desc *) (par->metromem + cmd_size
- + wfm_size + img_size + padding_size);
- par->metromem_desc_dma = par->metromem_dma + cmd_size + wfm_size
- + img_size + padding_size;
+ par->metromem_img_csum = (u16 *) (par->metromem_img + (fw * fh));
/* load the waveform in. assume mode 3, temp 31 for now
a) request the waveform file from userspace
@@ -658,7 +694,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
retval = request_firmware(&fw_entry, "metronome.wbf", &dev->dev);
if (retval < 0) {
dev_err(&dev->dev, "Failed to get waveform\n");
- goto err_dma_free;
+ goto err_csum_table;
}
retval = load_waveform((u8 *) fw_entry->data, fw_entry->size, 3, 31,
@@ -666,11 +702,11 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
release_firmware(fw_entry);
if (retval < 0) {
dev_err(&dev->dev, "Failed processing waveform\n");
- goto err_dma_free;
+ goto err_csum_table;
}
if (board->setup_irq(info))
- goto err_dma_free;
+ goto err_csum_table;
retval = metronome_init_regs(par);
if (retval < 0)
@@ -684,7 +720,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
retval = fb_alloc_cmap(&info->cmap, 8, 0);
if (retval < 0) {
dev_err(&dev->dev, "Failed to allocate colormap\n");
- goto err_fb_rel;
+ goto err_free_irq;
}
/* set cmap */
@@ -707,17 +743,15 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
err_cmap:
fb_dealloc_cmap(&info->cmap);
-err_fb_rel:
- framebuffer_release(info);
err_free_irq:
- board->free_irq(info);
-err_dma_free:
- dma_free_writecombine(&dev->dev, par->metromemsize, par->metromem,
- par->metromem_dma);
+ board->cleanup(par);
err_csum_table:
vfree(par->csum_table);
err_vfree:
vfree(videomemory);
+err_fb_rel:
+ framebuffer_release(info);
+err:
module_put(board->owner);
return retval;
}
@@ -728,15 +762,15 @@ static int __devexit metronomefb_remove(struct platform_device *dev)
if (info) {
struct metronomefb_par *par = info->par;
+
+ unregister_framebuffer(info);
fb_deferred_io_cleanup(info);
- dma_free_writecombine(&dev->dev, par->metromemsize,
- par->metromem, par->metromem_dma);
fb_dealloc_cmap(&info->cmap);
+ par->board->cleanup(par);
vfree(par->csum_table);
- unregister_framebuffer(info);
vfree((void __force *)info->screen_base);
- par->board->free_irq(info);
module_put(par->board->owner);
+ dev_dbg(&dev->dev, "calling release\n");
framebuffer_release(info);
}
return 0;
@@ -761,6 +795,9 @@ static void __exit metronomefb_exit(void)
platform_driver_unregister(&metronomefb_driver);
}
+module_param(user_wfm_size, uint, 0);
+MODULE_PARM_DESC(user_wfm_size, "Set custom waveform size");
+
module_init(metronomefb_init);
module_exit(metronomefb_exit);
diff --git a/include/video/metronomefb.h b/include/video/metronomefb.h
index dab04b4..79444cd 100644
--- a/include/video/metronomefb.h
+++ b/include/video/metronomefb.h
@@ -12,14 +12,6 @@
#ifndef _LINUX_METRONOMEFB_H_
#define _LINUX_METRONOMEFB_H_
-/* address and control descriptors used by metronome controller */
-struct metromem_desc {
- u32 mFDADR0;
- u32 mFSADR0;
- u32 mFIDR0;
- u32 mLDCMD0;
-};
-
/* command structure used by metronome controller */
struct metromem_cmd {
u16 opcode;
@@ -30,33 +22,33 @@ struct metromem_cmd {
/* struct used by metronome. board specific stuff comes from *board */
struct metronomefb_par {
unsigned char *metromem;
- struct metromem_desc *metromem_desc;
struct metromem_cmd *metromem_cmd;
unsigned char *metromem_wfm;
unsigned char *metromem_img;
u16 *metromem_img_csum;
u16 *csum_table;
- int metromemsize;
dma_addr_t metromem_dma;
- dma_addr_t metromem_desc_dma;
struct fb_info *info;
struct metronome_board *board;
wait_queue_head_t waitq;
u8 frame_count;
+ int extra_size;
+ int dt;
};
/* board specific routines */
struct metronome_board {
struct module *owner;
- void (*free_irq)(struct fb_info *);
- void (*init_gpio_regs)(struct metronomefb_par *);
- void (*init_lcdc_regs)(struct metronomefb_par *);
- void (*post_dma_setup)(struct metronomefb_par *);
+ struct module *fbmaster;
void (*set_rst)(struct metronomefb_par *, int);
void (*set_stdby)(struct metronomefb_par *, int);
+ void (*cleanup)(struct metronomefb_par *);
int (*met_wait_event)(struct metronomefb_par *);
int (*met_wait_event_intr)(struct metronomefb_par *);
int (*setup_irq)(struct fb_info *);
+ int (*setup_fb)(struct metronomefb_par *);
+ int (*setup_io)(struct metronomefb_par *);
+ int (*get_panel_type)(void);
};
#endif
--
1.5.3.6
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 2/5] gumstix: conversion to MFP support and add bluetooth support
2008-07-20 6:10 ` [RFC 2.6.26-rc9 2/5] gumstix: conversion to MFP support and add bluetooth support Jaya Kumar
@ 2008-07-21 2:13 ` eric miao
0 siblings, 0 replies; 18+ messages in thread
From: eric miao @ 2008-07-21 2:13 UTC (permalink / raw)
To: Jaya Kumar; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Sun, Jul 20, 2008 at 2:10 PM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
> This patch converts gumstix over to the MFP configuration system and adds
> bluetooth support.
>
Looks OK to me, except you seem to forget the gpio_request() in
gumstix_bluetooth_init(), with that change,
Acked-by: Eric Miao <eric.miao@marvell.com>
> Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
> ---
> arch/arm/mach-pxa/gumstix.c | 94 +++++++++++++++++++++++++++++++++++--------
> 1 files changed, 77 insertions(+), 17 deletions(-)
>
> diff --git a/arch/arm/mach-pxa/gumstix.c b/arch/arm/mach-pxa/gumstix.c
> index bdf2397..06493ff 100644
> --- a/arch/arm/mach-pxa/gumstix.c
> +++ b/arch/arm/mach-pxa/gumstix.c
> @@ -20,8 +20,12 @@
> #include <linux/init.h>
> #include <linux/platform_device.h>
> #include <linux/interrupt.h>
> +#include <linux/delay.h>
> #include <linux/mtd/mtd.h>
> #include <linux/mtd/partitions.h>
> +#include <linux/gpio.h>
> +#include <linux/err.h>
> +#include <linux/clk.h>
>
> #include <asm/setup.h>
> #include <asm/memory.h>
> @@ -40,7 +44,7 @@
>
> #include <asm/arch/pxa-regs.h>
> #include <asm/arch/pxa2xx-regs.h>
> -#include <asm/arch/pxa2xx-gpio.h>
> +#include <asm/arch/mfp-pxa25x.h>
>
> #include "generic.h"
>
> @@ -85,21 +89,8 @@ static struct platform_device *devices[] __initdata = {
> };
>
> #ifdef CONFIG_MMC_PXA
> -static struct pxamci_platform_data gumstix_mci_platform_data;
> -
> -static int gumstix_mci_init(struct device *dev, irq_handler_t detect_int,
> - void *data)
> -{
> - pxa_gpio_mode(GPIO6_MMCCLK_MD);
> - pxa_gpio_mode(GPIO53_MMCCLK_MD);
> - pxa_gpio_mode(GPIO8_MMCCS0_MD);
> -
> - return 0;
> -}
> -
> static struct pxamci_platform_data gumstix_mci_platform_data = {
> .ocr_mask = MMC_VDD_32_33|MMC_VDD_33_34,
> - .init = gumstix_mci_init,
> };
>
> static void __init gumstix_mmc_init(void)
> @@ -109,11 +100,11 @@ static void __init gumstix_mmc_init(void)
> #else
> static void __init gumstix_mmc_init(void)
> {
> - printk(KERN_INFO "Gumstix mmc disabled\n");
> + pr_debug("Gumstix mmc disabled\n");
> }
> #endif
>
> -#ifdef CONFIG_USB_GADGET_PXA2XX
> +#ifdef CONFIG_USB_GADGET_PXA25X
> static struct pxa2xx_udc_mach_info gumstix_udc_info __initdata = {
> .gpio_vbus = GPIO_GUMSTIX_USB_GPIOn,
> .gpio_pullup = GPIO_GUMSTIX_USB_GPIOx,
> @@ -126,12 +117,81 @@ static void __init gumstix_udc_init(void)
> #else
> static void gumstix_udc_init(void)
> {
> - printk(KERN_INFO "Gumstix udc is disabled\n");
> + pr_debug("Gumstix udc is disabled\n");
> }
> #endif
>
> +#ifdef CONFIG_BT
> +/* Normally, the bootloader would have enabled this 32kHz clock but many
> +** boards still have u-boot 1.1.4 so we check if it has been turned on and
> +** if not, we turn it on with a warning message. */
> +static void gumstix_setup_bt_clock(void)
> +{
> + int timeout = 500;
> +
> + if (!(OSCC & OSCC_OOK))
> + pr_warning("32kHz clock was not on. Bootloader may need to "
> + "be updated\n");
> + else
> + return;
> +
> + OSCC |= OSCC_OON;
> + do {
> + if (OSCC & OSCC_OOK)
> + break;
> + udelay(1);
> + } while (--timeout);
> + if (!timeout)
> + pr_err("Failed to start 32kHz clock\n");
> +}
> +
> +static void __init gumstix_bluetooth_init(void)
> +{
> + int err;
> +
> + gumstix_setup_bt_clock();
> +
> + err = gpio_direction_output(GPIO_GUMSTIX_BTRESET, 1);
> + if (err) {
> + pr_err("gumstix: can't reset bluetooth\n");
> + return;
> + }
> + gpio_set_value(GPIO_GUMSTIX_BTRESET, 0);
> + udelay(100);
> + gpio_set_value(GPIO_GUMSTIX_BTRESET, 1);
> +}
> +#else
> +static void gumstix_bluetooth_init(void)
> +{
> + pr_debug("Gumstix Bluetooth is disabled\n");
> +}
> +#endif
> +
> +static unsigned long gumstix_pin_config[] __initdata = {
> + GPIO12_32KHz,
> + /* BTUART */
> + GPIO42_HWUART_RXD,
> + GPIO43_HWUART_TXD,
> + GPIO44_HWUART_CTS,
> + GPIO45_HWUART_RTS,
> + /* MMC */
> + GPIO6_MMC_CLK,
> + GPIO53_MMC_CLK,
> + GPIO8_MMC_CS0,
> + /* these are used by AM200EPD */
> + GPIO51_GPIO,
> + GPIO49_GPIO,
> + GPIO48_GPIO,
> + GPIO32_GPIO,
> + GPIO17_GPIO,
> + GPIO16_GPIO,
> +};
> +
> static void __init gumstix_init(void)
> {
> + pxa2xx_mfp_config(ARRAY_AND_SIZE(gumstix_pin_config));
> +
> + gumstix_bluetooth_init();
> gumstix_udc_init();
> gumstix_mmc_init();
> (void) platform_add_devices(devices, ARRAY_SIZE(devices));
> --
> 1.5.3.6
>
>
> -------------------------------------------------------------------
> List admin: http://lists.arm.linux.org.uk/mailman/listinfo/linux-arm-kernel
> FAQ: http://www.arm.linux.org.uk/mailinglists/faq.php
> Etiquette: http://www.arm.linux.org.uk/mailinglists/etiquette.php
>
--
Cheers
- eric
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface
2008-07-20 6:10 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
@ 2008-07-21 11:11 ` Russell King - ARM Linux
2008-07-21 12:32 ` Jaya Kumar
0 siblings, 1 reply; 18+ messages in thread
From: Russell King - ARM Linux @ 2008-07-21 11:11 UTC (permalink / raw)
To: Jaya Kumar; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Sun, Jul 20, 2008 at 02:10:29AM -0400, Jaya Kumar wrote:
> if (fbi->map_cpu) {
> /* prevent initial garbage on screen */
> memset(fbi->map_cpu, 0, fbi->map_size);
> - fbi->fb.screen_base = fbi->map_cpu + fbi->video_offset;
> + fbi->fb.screen_base = (char __force __iomem *) fbi->map_cpu
> + + fbi->video_offset;
I'm not sure this has any benefits - the use of __force in drivers is
definitely frowned upon.
It's well known that FB doesn't sit well with all the MMIO sparse checking
so it's probably a good idea not to try and make it work.
> @@ -1357,6 +1379,8 @@ static void pxafb_decode_mode_info(struct pxafb_info *fbi,
> smemlen = modes[i].xres * modes[i].yres * modes[i].bpp / 8;
> if (smemlen > fbi->fb.fix.smem_len)
> fbi->fb.fix.smem_len = smemlen;
> + if (inf->custom_xfer_div)
> + fbi->fb.fix.smem_len /= inf->custom_xfer_div;
I don't understand this. If you have a 640x480 display with 8 bits of
memory per pixel, then it's 307200 bytes no matter whether you're only
using the lower 4 bits and the upper 4 are unused.
If, on the other hand, the lower 4 bits contain one pixel and the upper
4 bits contain the other pixel, then you have a 4 bit per pixel
framebuffer, so 'bpp' should be 4. In which case the original calculation
gives the correct answer.
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface
2008-07-21 11:11 ` Russell King - ARM Linux
@ 2008-07-21 12:32 ` Jaya Kumar
2008-07-21 13:53 ` SSP based framebuffer driver Blaine Booher
2008-07-26 3:30 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
0 siblings, 2 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-21 12:32 UTC (permalink / raw)
To: Russell King - ARM Linux; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Mon, Jul 21, 2008 at 7:11 AM, Russell King - ARM Linux
<linux@arm.linux.org.uk> wrote:
> On Sun, Jul 20, 2008 at 02:10:29AM -0400, Jaya Kumar wrote:
>> if (fbi->map_cpu) {
>> /* prevent initial garbage on screen */
>> memset(fbi->map_cpu, 0, fbi->map_size);
>> - fbi->fb.screen_base = fbi->map_cpu + fbi->video_offset;
>> + fbi->fb.screen_base = (char __force __iomem *) fbi->map_cpu
>> + + fbi->video_offset;
>
> I'm not sure this has any benefits - the use of __force in drivers is
> definitely frowned upon.
>
> It's well known that FB doesn't sit well with all the MMIO sparse checking
> so it's probably a good idea not to try and make it work.
Ok, I'll take it out. My intentions were to avoid causing any new
sparse warnings.
>
>> @@ -1357,6 +1379,8 @@ static void pxafb_decode_mode_info(struct pxafb_info *fbi,
>> smemlen = modes[i].xres * modes[i].yres * modes[i].bpp / 8;
>> if (smemlen > fbi->fb.fix.smem_len)
>> fbi->fb.fix.smem_len = smemlen;
>> + if (inf->custom_xfer_div)
>> + fbi->fb.fix.smem_len /= inf->custom_xfer_div;
>
> I don't understand this. If you have a 640x480 display with 8 bits of
> memory per pixel, then it's 307200 bytes no matter whether you're only
> using the lower 4 bits and the upper 4 are unused.
>
> If, on the other hand, the lower 4 bits contain one pixel and the upper
> 4 bits contain the other pixel, then you have a 4 bit per pixel
> framebuffer, so 'bpp' should be 4. In which case the original calculation
> gives the correct answer.
>
The complexity I faced is that the transfers used by Metronome on the
AMLCD bus have to be 16-bits wide although it is actually treating the
pixels as 8-bits per pixel and then only using the lower 4-bits within
that for actual content. So what I did in the code is set bits per
pixel, bpp to 16 so that pxafb sets the LCCR3_16BPP flag (so that it
meets Metronome's AMLCD transfer requirements) and then use the
custom_xfer_div to divide the transfer sizes and buffer allocations to
the correct size.
If I set bpp to 8, the allocations and transfer sizes are correct but
then that causes pxafb to set LCCR3_8BPP and that causes Metronome to
fail to display anything.
Instead of doing custom_xfer_div, I had thought about setting
pxafb_mach_info.lccr3 = LCCR3_16BPP to try to force the setting of
LCCR3_16BPP but then I saw:
include/asm/arch-pxa/pxafb.h
* The following should not be defined in LCCR3
* LCCR3_HSP, LCCR3_VSP, LCCR0_Pcd(x), LCCR3_Bpp
*/
u_int lccr3;
so I decided to create custom_xfer_div instead. How about if I try a
different way like creating a separate flag that can be used to
predicate the lccr3 setting. Maybe something like:
static int pxafb_bpp_to_lccr3(struct fb_var_screeninfo *var)
...
case 8:
switch (inf->custom_amlcd_bpp) {
case 16: ret = LCCR3_16BPP; break;
default: ret = LCCR3_8BPP; break;
case 16: ret = LCCR3_16BPP; break;
Thanks,
jaya
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* SSP based framebuffer driver
2008-07-21 12:32 ` Jaya Kumar
@ 2008-07-21 13:53 ` Blaine Booher
2008-07-26 3:30 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
1 sibling, 0 replies; 18+ messages in thread
From: Blaine Booher @ 2008-07-21 13:53 UTC (permalink / raw)
To: linux-fbdev-devel
Hey everyone,
I am hoping that this list can provide some insight into an issue that I'm trying to figure out. I am
working with a Gumstix platform using an ssp driven LCD screen. We can talk to the LCD screen
over the ssp pins, and we even have a driver that maps it to a /dev/ file.
We would ultimately like to have this device working as a framebuffer driven device. I don't know
enough about framebuffers, yet, but am reading as much as possible.
So my questions are:
* Can anyone recommend any basic literature for diving into this?
* Has anyone seen or heard of this kind of functionality?
* Do any projects exist relating to this?
* From my understanding thus far, we would want to implement our own /dev/fb0 (or similar) that
took X Server commands and throws them out to the ssp device. Is this the right kind of thinking?
Thank you!
Blaine
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface
2008-07-21 12:32 ` Jaya Kumar
2008-07-21 13:53 ` SSP based framebuffer driver Blaine Booher
@ 2008-07-26 3:30 ` Jaya Kumar
2008-07-30 2:41 ` Eric Miao
1 sibling, 1 reply; 18+ messages in thread
From: Jaya Kumar @ 2008-07-26 3:30 UTC (permalink / raw)
To: Russell King - ARM Linux; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Mon, Jul 21, 2008 at 8:32 AM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
> On Mon, Jul 21, 2008 at 7:11 AM, Russell King - ARM Linux
> <linux@arm.linux.org.uk> wrote:
>> On Sun, Jul 20, 2008 at 02:10:29AM -0400, Jaya Kumar wrote:
>>
>>> @@ -1357,6 +1379,8 @@ static void pxafb_decode_mode_info(struct pxafb_info *fbi,
>>> smemlen = modes[i].xres * modes[i].yres * modes[i].bpp / 8;
>>> if (smemlen > fbi->fb.fix.smem_len)
>>> fbi->fb.fix.smem_len = smemlen;
>>> + if (inf->custom_xfer_div)
>>> + fbi->fb.fix.smem_len /= inf->custom_xfer_div;
>>
>> I don't understand this. If you have a 640x480 display with 8 bits of
>> memory per pixel, then it's 307200 bytes no matter whether you're only
>> using the lower 4 bits and the upper 4 are unused.
>>
>> If, on the other hand, the lower 4 bits contain one pixel and the upper
>> 4 bits contain the other pixel, then you have a 4 bit per pixel
>> framebuffer, so 'bpp' should be 4. In which case the original calculation
>> gives the correct answer.
>>
>
> The complexity I faced is that the transfers used by Metronome on the
> AMLCD bus have to be 16-bits wide although it is actually treating the
> pixels as 8-bits per pixel and then only using the lower 4-bits within
> that for actual content. So what I did in the code is set bits per
> pixel, bpp to 16 so that pxafb sets the LCCR3_16BPP flag (so that it
> meets Metronome's AMLCD transfer requirements) and then use the
> custom_xfer_div to divide the transfer sizes and buffer allocations to
> the correct size.
>
> If I set bpp to 8, the allocations and transfer sizes are correct but
> then that causes pxafb to set LCCR3_8BPP and that causes Metronome to
> fail to display anything.
>
> Instead of doing custom_xfer_div, I had thought about setting
> pxafb_mach_info.lccr3 = LCCR3_16BPP to try to force the setting of
> LCCR3_16BPP but then I saw:
>
> include/asm/arch-pxa/pxafb.h
> * The following should not be defined in LCCR3
> * LCCR3_HSP, LCCR3_VSP, LCCR0_Pcd(x), LCCR3_Bpp
> */
> u_int lccr3;
>
> so I decided to create custom_xfer_div instead. How about if I try a
> different way like creating a separate flag that can be used to
> predicate the lccr3 setting. Maybe something like:
>
> static int pxafb_bpp_to_lccr3(struct fb_var_screeninfo *var)
> ...
> case 8:
> switch (inf->custom_amlcd_bpp) {
> case 16: ret = LCCR3_16BPP; break;
> default: ret = LCCR3_8BPP; break;
> case 16: ret = LCCR3_16BPP; break;
>
> Thanks,
> jaya
>
I took a look at doing the above, ie: adjusting bpp instead of
custom_xfer_size. I've realized that I would still need to adjust lccr
in at least one other place:
fbi->reg_lccr1 =
LCCR1_DisWdth(var->xres) +
I'll try to improve my explanation. :-)
The reason for this is that metronome requires a different bus width
(16 bit) for AMLCD transfers than it requires for its expected bits
per pixel ( 8 bits). To get LCDC to use 16 bits on the AMLCD bus, we
need to set 16bpp in LCCR3. So we then need to divide down the x
resolution in LCCR1. Eg: 800 pixels at 8bpp is the framebuffer. We
need 16-bit transfers so we set the desired pixels per line in LCCR to
= 800 pixels / ( 16 custom bus bits / 8 bits per pixel ) = 400 pixels
per line. So the code would be like:
pix_per_line = var->xres / ( inf->custom_lccr_bpp / var->bits_per_pixel )
I hope I was able to explain my reasoning for this above.
Thanks,
jaya
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages
2008-07-26 4:32 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v7 Jaya Kumar
@ 2008-07-26 4:32 ` Jaya Kumar
2008-07-30 2:50 ` Eric Miao
0 siblings, 1 reply; 18+ messages in thread
From: Jaya Kumar @ 2008-07-26 4:32 UTC (permalink / raw)
To: ymiao3; +Cc: Jaya Kumar, linux-fbdev-devel, linux-arm-kernel
This patch converts the printk messages in metronomefb to dev_dbg/err type
messages.
Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
---
drivers/video/metronomefb.c | 49 +++++++++++++++++++-----------------------
1 files changed, 22 insertions(+), 27 deletions(-)
diff --git a/drivers/video/metronomefb.c b/drivers/video/metronomefb.c
index cc4c038..8ccd113 100644
--- a/drivers/video/metronomefb.c
+++ b/drivers/video/metronomefb.c
@@ -18,6 +18,8 @@
* is provided as am200epd.c
*
*/
+#define DEBUG 1
+
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
@@ -40,15 +42,6 @@
#include <asm/unaligned.h>
-
-#define DEBUG 1
-#ifdef DEBUG
-#define DPRINTK(f, a...) printk(KERN_DEBUG "%s: " f, __func__ , ## a)
-#else
-#define DPRINTK(f, a...)
-#endif
-
-
/* Display specific information */
#define DPY_W 832
#define DPY_H 622
@@ -135,8 +128,8 @@ static u16 calc_img_cksum(u16 *start, int length)
/* here we decode the incoming waveform file and populate metromem */
#define EXP_WFORM_SIZE 47001
-static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
- u8 *frame_count)
+static int __devinit load_waveform(u8 *mem, size_t size, int m, int t,
+ struct metronomefb_par *par)
{
int tta;
int wmta;
@@ -148,9 +141,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
int wfm_idx, owfm_idx;
int mem_idx = 0;
struct waveform_hdr *wfm_hdr;
+ u8 *metromem = par->metromem_wfm;
+ struct device *dev = par->info->dev;
if (size != EXP_WFORM_SIZE) {
- printk(KERN_ERR "Error: unexpected size %d != %d\n", size,
+ dev_err(dev, "Error: unexpected size %d != %d\n", size,
EXP_WFORM_SIZE);
return -EINVAL;
}
@@ -158,16 +153,16 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
wfm_hdr = (struct waveform_hdr *) mem;
if (wfm_hdr->fvsn != 1) {
- printk(KERN_ERR "Error: bad fvsn %x\n", wfm_hdr->fvsn);
+ dev_err(dev, "Error: bad fvsn %x\n", wfm_hdr->fvsn);
return -EINVAL;
}
if (wfm_hdr->luts != 0) {
- printk(KERN_ERR "Error: bad luts %x\n", wfm_hdr->luts);
+ dev_err(dev, "Error: bad luts %x\n", wfm_hdr->luts);
return -EINVAL;
}
cksum = calc_cksum(32, 47, mem);
if (cksum != wfm_hdr->wfm_cs) {
- printk(KERN_ERR "Error: bad cksum %x != %x\n", cksum,
+ dev_err(dev, "Error: bad cksum %x != %x\n", cksum,
wfm_hdr->wfm_cs);
return -EINVAL;
}
@@ -175,7 +170,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
wfm_hdr->trc += 1;
for (i = 0; i < 5; i++) {
if (*(wfm_hdr->stuff2a + i) != 0) {
- printk(KERN_ERR "Error: unexpected value in padding\n");
+ dev_err(dev, "Error: unexpected value in padding\n");
return -EINVAL;
}
}
@@ -200,7 +195,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(sizeof(*wfm_hdr), cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad temperature range table cksum"
+ dev_err(dev, "Error: bad temperature range table cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -212,7 +207,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad mode table address cksum"
+ dev_err(dev, "Error: bad mode table address cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -224,7 +219,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad temperature table address cksum"
+ dev_err(dev, "Error: bad temperature table address cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
@@ -259,11 +254,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
return -EINVAL;
cksum = calc_cksum(owfm_idx, cksum_idx, mem);
if (cksum != mem[cksum_idx]) {
- printk(KERN_ERR "Error: bad waveform data cksum"
+ dev_err(dev, "Error: bad waveform data cksum"
" %x != %x\n", cksum, mem[cksum_idx]);
return -EINVAL;
}
- *frame_count = (mem_idx/64);
+ par->frame_count = (mem_idx/64);
return 0;
}
@@ -662,15 +657,15 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
b) process waveform and decode into metromem */
retval = request_firmware(&fw_entry, "metronome.wbf", &dev->dev);
if (retval < 0) {
- printk(KERN_ERR "metronomefb: couldn't get waveform\n");
+ dev_err(&dev->dev, "Failed to get waveform\n");
goto err_dma_free;
}
- retval = load_waveform((u8 *) fw_entry->data, fw_entry->size,
- par->metromem_wfm, 3, 31, &par->frame_count);
+ retval = load_waveform((u8 *) fw_entry->data, fw_entry->size, 3, 31,
+ par);
release_firmware(fw_entry);
if (retval < 0) {
- printk(KERN_ERR "metronomefb: couldn't process waveform\n");
+ dev_err(&dev->dev, "Failed processing waveform\n");
goto err_dma_free;
}
@@ -688,7 +683,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
retval = fb_alloc_cmap(&info->cmap, 8, 0);
if (retval < 0) {
- printk(KERN_ERR "Failed to allocate colormap\n");
+ dev_err(&dev->dev, "Failed to allocate colormap\n");
goto err_fb_rel;
}
@@ -704,7 +699,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
platform_set_drvdata(dev, info);
- printk(KERN_INFO
+ dev_dbg(&dev->dev,
"fb%d: Metronome frame buffer device, using %dK of video"
" memory\n", info->node, videomemorysize >> 10);
--
1.5.3.6
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface
2008-07-26 3:30 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
@ 2008-07-30 2:41 ` Eric Miao
2008-07-30 3:10 ` Jaya Kumar
0 siblings, 1 reply; 18+ messages in thread
From: Eric Miao @ 2008-07-30 2:41 UTC (permalink / raw)
To: Jaya Kumar
Cc: linux-fbdev-devel, ymiao3, Russell King - ARM Linux,
linux-arm-kernel
On Sat, Jul 26, 2008 at 11:30 AM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
> On Mon, Jul 21, 2008 at 8:32 AM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
>> On Mon, Jul 21, 2008 at 7:11 AM, Russell King - ARM Linux
>> <linux@arm.linux.org.uk> wrote:
>>> On Sun, Jul 20, 2008 at 02:10:29AM -0400, Jaya Kumar wrote:
>>>
>>>> @@ -1357,6 +1379,8 @@ static void pxafb_decode_mode_info(struct pxafb_info *fbi,
>>>> smemlen = modes[i].xres * modes[i].yres * modes[i].bpp / 8;
>>>> if (smemlen > fbi->fb.fix.smem_len)
>>>> fbi->fb.fix.smem_len = smemlen;
>>>> + if (inf->custom_xfer_div)
>>>> + fbi->fb.fix.smem_len /= inf->custom_xfer_div;
>>>
>>> I don't understand this. If you have a 640x480 display with 8 bits of
>>> memory per pixel, then it's 307200 bytes no matter whether you're only
>>> using the lower 4 bits and the upper 4 are unused.
>>>
>>> If, on the other hand, the lower 4 bits contain one pixel and the upper
>>> 4 bits contain the other pixel, then you have a 4 bit per pixel
>>> framebuffer, so 'bpp' should be 4. In which case the original calculation
>>> gives the correct answer.
>>>
>>
>> The complexity I faced is that the transfers used by Metronome on the
>> AMLCD bus have to be 16-bits wide although it is actually treating the
>> pixels as 8-bits per pixel and then only using the lower 4-bits within
>> that for actual content. So what I did in the code is set bits per
>> pixel, bpp to 16 so that pxafb sets the LCCR3_16BPP flag (so that it
>> meets Metronome's AMLCD transfer requirements) and then use the
>> custom_xfer_div to divide the transfer sizes and buffer allocations to
>> the correct size.
>>
>> If I set bpp to 8, the allocations and transfer sizes are correct but
>> then that causes pxafb to set LCCR3_8BPP and that causes Metronome to
>> fail to display anything.
>>
>> Instead of doing custom_xfer_div, I had thought about setting
>> pxafb_mach_info.lccr3 = LCCR3_16BPP to try to force the setting of
>> LCCR3_16BPP but then I saw:
>>
>> include/asm/arch-pxa/pxafb.h
>> * The following should not be defined in LCCR3
>> * LCCR3_HSP, LCCR3_VSP, LCCR0_Pcd(x), LCCR3_Bpp
>> */
>> u_int lccr3;
>>
>> so I decided to create custom_xfer_div instead. How about if I try a
>> different way like creating a separate flag that can be used to
>> predicate the lccr3 setting. Maybe something like:
>>
>> static int pxafb_bpp_to_lccr3(struct fb_var_screeninfo *var)
>> ...
>> case 8:
>> switch (inf->custom_amlcd_bpp) {
>> case 16: ret = LCCR3_16BPP; break;
>> default: ret = LCCR3_8BPP; break;
>> case 16: ret = LCCR3_16BPP; break;
>>
>> Thanks,
>> jaya
>>
>
> I took a look at doing the above, ie: adjusting bpp instead of
> custom_xfer_size. I've realized that I would still need to adjust lccr
> in at least one other place:
>
> fbi->reg_lccr1 =
> LCCR1_DisWdth(var->xres) +
>
> I'll try to improve my explanation. :-)
>
> The reason for this is that metronome requires a different bus width
> (16 bit) for AMLCD transfers than it requires for its expected bits
> per pixel ( 8 bits). To get LCDC to use 16 bits on the AMLCD bus, we
> need to set 16bpp in LCCR3. So we then need to divide down the x
> resolution in LCCR1. Eg: 800 pixels at 8bpp is the framebuffer. We
> need 16-bit transfers so we set the desired pixels per line in LCCR to
> = 800 pixels / ( 16 custom bus bits / 8 bits per pixel ) = 400 pixels
> per line. So the code would be like:
>
> pix_per_line = var->xres / ( inf->custom_lccr_bpp / var->bits_per_pixel )
>
> I hope I was able to explain my reasoning for this above.
>
Sorry for the delay, I begin to understand the way this metronome is
working, so each transfer is 16-bit wide and contains two 8-bit pixels?
Then the most simple way is to treat this display as 16-bit, and
adjust the resolution parameters in the platform data with a nice
comment.
The problem of doing so is that:
1) framebuffer console cann't work anymore, and will show garbage
instead of showing the nice penguine logo
2) the framebuffer application has to be aware of this, and handles
the pixel format correctly.
Provided the fact of this weird organized pixel format, I don't see many
chances that X window or console can be run on top of this, but a
specialized application, no?
> Thanks,
> jaya
>
> -------------------------------------------------------------------
> List admin: http://lists.arm.linux.org.uk/mailman/listinfo/linux-arm-kernel
> FAQ: http://www.arm.linux.org.uk/mailinglists/faq.php
> Etiquette: http://www.arm.linux.org.uk/mailinglists/etiquette.php
>
--
Cheers
- eric
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages
2008-07-26 4:32 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
@ 2008-07-30 2:50 ` Eric Miao
2008-07-30 3:18 ` Jaya Kumar
0 siblings, 1 reply; 18+ messages in thread
From: Eric Miao @ 2008-07-30 2:50 UTC (permalink / raw)
To: Jaya Kumar; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Sat, Jul 26, 2008 at 12:32 PM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
> This patch converts the printk messages in metronomefb to dev_dbg/err type
> messages.
>
I think this is already Acked (except for the DEBUG definition), so it would
probably nice if you can re-order the patch series and put this in the front,
so the next time we can focus on those patches with concerns only, and
get things merged a bit quicker.
That will take you sometime, though. Sorry about that and thanks for the
good work.
> Signed-off-by: Jaya Kumar <jayakumar.lkml@gmail.com>
> ---
> drivers/video/metronomefb.c | 49 +++++++++++++++++++-----------------------
> 1 files changed, 22 insertions(+), 27 deletions(-)
>
> diff --git a/drivers/video/metronomefb.c b/drivers/video/metronomefb.c
> index cc4c038..8ccd113 100644
> --- a/drivers/video/metronomefb.c
> +++ b/drivers/video/metronomefb.c
> @@ -18,6 +18,8 @@
> * is provided as am200epd.c
> *
> */
> +#define DEBUG 1
> +
> #include <linux/module.h>
> #include <linux/kernel.h>
> #include <linux/errno.h>
> @@ -40,15 +42,6 @@
>
> #include <asm/unaligned.h>
>
> -
> -#define DEBUG 1
> -#ifdef DEBUG
> -#define DPRINTK(f, a...) printk(KERN_DEBUG "%s: " f, __func__ , ## a)
> -#else
> -#define DPRINTK(f, a...)
> -#endif
> -
> -
> /* Display specific information */
> #define DPY_W 832
> #define DPY_H 622
> @@ -135,8 +128,8 @@ static u16 calc_img_cksum(u16 *start, int length)
>
> /* here we decode the incoming waveform file and populate metromem */
> #define EXP_WFORM_SIZE 47001
> -static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> - u8 *frame_count)
> +static int __devinit load_waveform(u8 *mem, size_t size, int m, int t,
> + struct metronomefb_par *par)
> {
> int tta;
> int wmta;
> @@ -148,9 +141,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> int wfm_idx, owfm_idx;
> int mem_idx = 0;
> struct waveform_hdr *wfm_hdr;
> + u8 *metromem = par->metromem_wfm;
> + struct device *dev = par->info->dev;
>
> if (size != EXP_WFORM_SIZE) {
> - printk(KERN_ERR "Error: unexpected size %d != %d\n", size,
> + dev_err(dev, "Error: unexpected size %d != %d\n", size,
> EXP_WFORM_SIZE);
> return -EINVAL;
> }
> @@ -158,16 +153,16 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> wfm_hdr = (struct waveform_hdr *) mem;
>
> if (wfm_hdr->fvsn != 1) {
> - printk(KERN_ERR "Error: bad fvsn %x\n", wfm_hdr->fvsn);
> + dev_err(dev, "Error: bad fvsn %x\n", wfm_hdr->fvsn);
> return -EINVAL;
> }
> if (wfm_hdr->luts != 0) {
> - printk(KERN_ERR "Error: bad luts %x\n", wfm_hdr->luts);
> + dev_err(dev, "Error: bad luts %x\n", wfm_hdr->luts);
> return -EINVAL;
> }
> cksum = calc_cksum(32, 47, mem);
> if (cksum != wfm_hdr->wfm_cs) {
> - printk(KERN_ERR "Error: bad cksum %x != %x\n", cksum,
> + dev_err(dev, "Error: bad cksum %x != %x\n", cksum,
> wfm_hdr->wfm_cs);
> return -EINVAL;
> }
> @@ -175,7 +170,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> wfm_hdr->trc += 1;
> for (i = 0; i < 5; i++) {
> if (*(wfm_hdr->stuff2a + i) != 0) {
> - printk(KERN_ERR "Error: unexpected value in padding\n");
> + dev_err(dev, "Error: unexpected value in padding\n");
> return -EINVAL;
> }
> }
> @@ -200,7 +195,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> return -EINVAL;
> cksum = calc_cksum(sizeof(*wfm_hdr), cksum_idx, mem);
> if (cksum != mem[cksum_idx]) {
> - printk(KERN_ERR "Error: bad temperature range table cksum"
> + dev_err(dev, "Error: bad temperature range table cksum"
> " %x != %x\n", cksum, mem[cksum_idx]);
> return -EINVAL;
> }
> @@ -212,7 +207,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> return -EINVAL;
> cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
> if (cksum != mem[cksum_idx]) {
> - printk(KERN_ERR "Error: bad mode table address cksum"
> + dev_err(dev, "Error: bad mode table address cksum"
> " %x != %x\n", cksum, mem[cksum_idx]);
> return -EINVAL;
> }
> @@ -224,7 +219,7 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> return -EINVAL;
> cksum = calc_cksum(cksum_idx - 3, cksum_idx, mem);
> if (cksum != mem[cksum_idx]) {
> - printk(KERN_ERR "Error: bad temperature table address cksum"
> + dev_err(dev, "Error: bad temperature table address cksum"
> " %x != %x\n", cksum, mem[cksum_idx]);
> return -EINVAL;
> }
> @@ -259,11 +254,11 @@ static int load_waveform(u8 *mem, size_t size, u8 *metromem, int m, int t,
> return -EINVAL;
> cksum = calc_cksum(owfm_idx, cksum_idx, mem);
> if (cksum != mem[cksum_idx]) {
> - printk(KERN_ERR "Error: bad waveform data cksum"
> + dev_err(dev, "Error: bad waveform data cksum"
> " %x != %x\n", cksum, mem[cksum_idx]);
> return -EINVAL;
> }
> - *frame_count = (mem_idx/64);
> + par->frame_count = (mem_idx/64);
>
> return 0;
> }
> @@ -662,15 +657,15 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
> b) process waveform and decode into metromem */
> retval = request_firmware(&fw_entry, "metronome.wbf", &dev->dev);
> if (retval < 0) {
> - printk(KERN_ERR "metronomefb: couldn't get waveform\n");
> + dev_err(&dev->dev, "Failed to get waveform\n");
> goto err_dma_free;
> }
>
> - retval = load_waveform((u8 *) fw_entry->data, fw_entry->size,
> - par->metromem_wfm, 3, 31, &par->frame_count);
> + retval = load_waveform((u8 *) fw_entry->data, fw_entry->size, 3, 31,
> + par);
> release_firmware(fw_entry);
> if (retval < 0) {
> - printk(KERN_ERR "metronomefb: couldn't process waveform\n");
> + dev_err(&dev->dev, "Failed processing waveform\n");
> goto err_dma_free;
> }
>
> @@ -688,7 +683,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
>
> retval = fb_alloc_cmap(&info->cmap, 8, 0);
> if (retval < 0) {
> - printk(KERN_ERR "Failed to allocate colormap\n");
> + dev_err(&dev->dev, "Failed to allocate colormap\n");
> goto err_fb_rel;
> }
>
> @@ -704,7 +699,7 @@ static int __devinit metronomefb_probe(struct platform_device *dev)
>
> platform_set_drvdata(dev, info);
>
> - printk(KERN_INFO
> + dev_dbg(&dev->dev,
> "fb%d: Metronome frame buffer device, using %dK of video"
> " memory\n", info->node, videomemorysize >> 10);
>
> --
> 1.5.3.6
>
>
> -------------------------------------------------------------------
> List admin: http://lists.arm.linux.org.uk/mailman/listinfo/linux-arm-kernel
> FAQ: http://www.arm.linux.org.uk/mailinglists/faq.php
> Etiquette: http://www.arm.linux.org.uk/mailinglists/etiquette.php
>
--
Cheers
- eric
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface
2008-07-30 2:41 ` Eric Miao
@ 2008-07-30 3:10 ` Jaya Kumar
0 siblings, 0 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-30 3:10 UTC (permalink / raw)
To: Eric Miao
Cc: linux-fbdev-devel, ymiao3, Russell King - ARM Linux,
linux-arm-kernel
On Tue, Jul 29, 2008 at 10:41 PM, Eric Miao <eric.y.miao@gmail.com> wrote:
> On Sat, Jul 26, 2008 at 11:30 AM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
>>
>> I took a look at doing the above, ie: adjusting bpp instead of
>> custom_xfer_size. I've realized that I would still need to adjust lccr
>> in at least one other place:
>>
>> fbi->reg_lccr1 =
>> LCCR1_DisWdth(var->xres) +
>>
>> I'll try to improve my explanation. :-)
>>
>> The reason for this is that metronome requires a different bus width
>> (16 bit) for AMLCD transfers than it requires for its expected bits
>> per pixel ( 8 bits). To get LCDC to use 16 bits on the AMLCD bus, we
>> need to set 16bpp in LCCR3. So we then need to divide down the x
>> resolution in LCCR1. Eg: 800 pixels at 8bpp is the framebuffer. We
>> need 16-bit transfers so we set the desired pixels per line in LCCR to
>> = 800 pixels / ( 16 custom bus bits / 8 bits per pixel ) = 400 pixels
>> per line. So the code would be like:
>>
>> pix_per_line = var->xres / ( inf->custom_lccr_bpp / var->bits_per_pixel )
>>
>> I hope I was able to explain my reasoning for this above.
>>
>
> Sorry for the delay, I begin to understand the way this metronome is
> working, so each transfer is 16-bit wide and contains two 8-bit pixels?
Correct, the AMLCD xfer is 16-bit wide and is treated by Metronome as
2 8-bit pixels.
>
> Then the most simple way is to treat this display as 16-bit, and
> adjust the resolution parameters in the platform data with a nice
> comment.
I originally had it as .bpp = 16 ( in v6 and before) and used
custom_xfer_data to divide down the buffer sizes. The resolution needs
to stay at 800x600 so that the reported resolution for the display is
correct. So've I changed that to .bpp = 8 and used custom_lccr_bpp to
set LCCR3 to 16bpp in v7. Let me know if the implementation in v7 is
consistent with your suggestion.
>
> The problem of doing so is that:
> 1) framebuffer console cann't work anymore, and will show garbage
> instead of showing the nice penguine logo
>
> 2) the framebuffer application has to be aware of this, and handles
> the pixel format correctly.
>
> Provided the fact of this weird organized pixel format, I don't see many
> chances that X window or console can be run on top of this, but a
> specialized application, no?
Deferred IO converts the pixel data organization for the Metronome
controller so the latter is transparent to anything above fbdev. I
have tested with Xfbdev and it works quite well. So no specialized
applications needed. :-) Some video clips of it running here:
http://youtube.com/watch?v=Or3R3Q8oyuE and also a LinuxJournal article
showing the display with dillo and other standard applications.
http://www.linuxjournal.com/article/10110
Thanks,
jaya
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages
2008-07-30 2:50 ` Eric Miao
@ 2008-07-30 3:18 ` Jaya Kumar
0 siblings, 0 replies; 18+ messages in thread
From: Jaya Kumar @ 2008-07-30 3:18 UTC (permalink / raw)
To: Eric Miao; +Cc: ymiao3, linux-fbdev-devel, linux-arm-kernel
On Tue, Jul 29, 2008 at 10:50 PM, Eric Miao <eric.y.miao@gmail.com> wrote:
> On Sat, Jul 26, 2008 at 12:32 PM, Jaya Kumar <jayakumar.lkml@gmail.com> wrote:
>> This patch converts the printk messages in metronomefb to dev_dbg/err type
>> messages.
>>
>
> I think this is already Acked (except for the DEBUG definition), so it would
> probably nice if you can re-order the patch series and put this in the front,
> so the next time we can focus on those patches with concerns only, and
> get things merged a bit quicker.
>
> That will take you sometime, though. Sorry about that and thanks for the
> good work.
Hi Eric,
No worries. Yup, I'll take DEBUG out before posting final. Thanks for
the review.
Regards,
jaya
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
^ permalink raw reply [flat|nested] 18+ messages in thread
end of thread, other threads:[~2008-07-30 3:18 UTC | newest]
Thread overview: 18+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-07-20 6:10 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v6 Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
2008-07-21 11:11 ` Russell King - ARM Linux
2008-07-21 12:32 ` Jaya Kumar
2008-07-21 13:53 ` SSP based framebuffer driver Blaine Booher
2008-07-26 3:30 ` [RFC 2.6.26-rc9 1/5] pxafb: add shared framebuffer interface Jaya Kumar
2008-07-30 2:41 ` Eric Miao
2008-07-30 3:10 ` Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 2/5] gumstix: conversion to MFP support and add bluetooth support Jaya Kumar
2008-07-21 2:13 ` eric miao
2008-07-20 6:10 ` [RFC 2.6.26-rc9 3/5] am200epd: convert to shared fb and use gpio api Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
2008-07-20 6:10 ` [RFC 2.6.26-rc9 5/5] metronomefb: changes to use separate framebuffer Jaya Kumar
-- strict thread matches above, loose matches on Subject: below --
2008-07-26 4:32 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v7 Jaya Kumar
2008-07-26 4:32 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
2008-07-30 2:50 ` Eric Miao
2008-07-30 3:18 ` Jaya Kumar
2008-07-13 13:26 [RFC 2.6.26-rc9 0/5] am200epd, pxafb, metronomefb changes v5 Jaya Kumar
2008-07-13 13:26 ` [RFC 2.6.26-rc9 4/5] metronomefb: convert printk to dev_dbg/err messages Jaya Kumar
2008-07-16 7:09 ` eric miao
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).