* framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
@ 2005-08-05 7:18 akpm
2005-08-05 9:47 ` Andrey Volkov
` (3 more replies)
0 siblings, 4 replies; 8+ messages in thread
From: akpm @ 2005-08-05 7:18 UTC (permalink / raw)
To: jamey, anpaza, linux-fbdev-devel, mm-commits
The patch titled
framebuffer driver for MQ11xx graphics chip
has been added to the -mm tree. Its filename is
framebuffer-driver-for-mq11xx-graphics-chip.patch
Patches currently in -mm which might be from jamey@handhelds.org are
platform-device-driver-for-mq11xx-graphics-chip.patch
framebuffer-driver-for-mq11xx-graphics-chip.patch
usb-gadget-driver-for-mq11xx-graphics-chip.patch
From: Jamey Hicks <jamey@handhelds.org>
This patch adds a framebuffer driver for MQ11xx system-on-chip graphics
chip. This chip is used in several non-PCI ARM and MIPS platforms such as
the iPAQ H5550. This driver depends on the overall platform_device driver
for the chip.
Signed-off-by: Jamey Hicks <jamey@handhelds.org>
Signed-off-by: Andrew Zabolotny <anpaza@mail.ru>
Cc: <linux-fbdev-devel@lists.sourceforge.net>
Signed-off-by: Andrew Morton <akpm@osdl.org>
---
drivers/video/Kconfig | 17 +
drivers/video/Makefile | 1
drivers/video/mq1100fb.c | 497 +++++++++++++++++++++++++++++++++++++++++++++++
3 files changed, 515 insertions(+)
diff -puN drivers/video/Kconfig~framebuffer-driver-for-mq11xx-graphics-chip drivers/video/Kconfig
--- devel/drivers/video/Kconfig~framebuffer-driver-for-mq11xx-graphics-chip 2005-08-05 00:18:05.000000000 -0700
+++ devel-akpm/drivers/video/Kconfig 2005-08-05 00:18:05.000000000 -0700
@@ -1438,6 +1438,23 @@ config FB_PXA
If unsure, say N.
+config FB_MQ1100
+ tristate "MQ1100/32/68/78/88 framebuffer support"
+ depends on FB && PLATFORM_MQ11XX
+ select FB_CFB_FILLRECT
+ select FB_CFB_COPYAREA
+ select FB_CFB_IMAGEBLIT
+ select FB_SOFT_CURSOR
+ help
+ This is a framebuffer device for the MediaQ 1100/32/68/78/88
+ LCD controllers (http://www.mediaq.com) found in some PDAs
+ (these include: iPAQ 5400, Axim X5, iPAQ 221x).
+
+ This driver handles only the LCD controller apect of the MediaQ;
+ other functions are handled in respective drivers.
+ See <http://www.linux-fbdev.org/> for information
+ on framebuffer devices.
+
config FB_W100
tristate "W100 frame buffer support"
depends on FB && PXA_SHARPSL
diff -puN drivers/video/Makefile~framebuffer-driver-for-mq11xx-graphics-chip drivers/video/Makefile
--- devel/drivers/video/Makefile~framebuffer-driver-for-mq11xx-graphics-chip 2005-08-05 00:18:05.000000000 -0700
+++ devel-akpm/drivers/video/Makefile 2005-08-05 00:18:05.000000000 -0700
@@ -83,6 +83,7 @@ obj-$(CONFIG_FB_GBE) += gbe
obj-$(CONFIG_FB_CIRRUS) += cirrusfb.o
obj-$(CONFIG_FB_ASILIANT) += asiliantfb.o
obj-$(CONFIG_FB_PXA) += pxafb.o
+obj-$(CONFIG_FB_MQ1100) += mq1100fb.o
obj-$(CONFIG_FB_W100) += w100fb.o
obj-$(CONFIG_FB_AU1100) += au1100fb.o fbgen.o
obj-$(CONFIG_FB_PMAG_AA) += pmag-aa-fb.o
diff -puN /dev/null drivers/video/mq1100fb.c
--- /dev/null 2003-09-15 06:40:47.000000000 -0700
+++ devel-akpm/drivers/video/mq1100fb.c 2005-08-05 00:18:05.000000000 -0700
@@ -0,0 +1,497 @@
+/*
+ * linux/drivers/mq1100fb.c
+ *
+ * Copyright © 2003 Keith Packard
+ *
+ * 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.
+ *
+ * MediaQ 1100/32/68/78/88 LCD Controller Frame Buffer Driver
+ *
+ * Please direct your questions and comments on this driver to the following
+ * email address:
+ *
+ * keithp@keithp.com
+ *
+ * ChangeLog
+ *
+ * 2003-12-06: Andrew Zabolotny <zap@homelink.ru>
+ * - Modified to use the MediaQ SoC base driver to allow
+ * sharing of other MediaQ subdevices with other drivers.
+ * 2003-05-18: <keithp@keithp.com>
+ * - Ported from PCI development board to ARM H5400
+ */
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/fb.h>
+#include <linux/init.h>
+#include <linux/device.h>
+#include <linux/notifier.h>
+#include <../drivers/platform/mq11xx.h>
+
+#if 0
+# define debug(s, args...) printk (KERN_INFO s, ##args)
+#else
+# define debug(s, args...)
+#endif
+#define debug_func(s, args...) debug ("%s: " s, __FUNCTION__, ##args)
+
+#define MQ_Rotate_0 1
+#define MQ_Rotate_90 2
+#define MQ_Rotate_180 4
+#define MQ_Rotate_270 8
+
+#define MQ_Reflect_X 16
+#define MQ_Reflect_Y 32
+
+struct mq1100fb_rgb {
+ unsigned char red,green,blue,transp;
+};
+
+struct mq1100fb_info {
+ /* Framebuffer info */
+ struct fb_info fb;
+ /* The link to the base SoC driver */
+ struct mediaq11xx_base *base;
+ /* The RGB palette */
+ struct mq1100fb_rgb palette[256];
+ /* Notifier block */
+ struct notifier_block notify;
+ /* Framebuffer offset inside MediaQ RAM */
+ u32 fb_addr, fb_size;
+ /* The pseudo-palette */
+ u32 pseudo_pal[16];
+ /* Device instance number (0-7) */
+ u8 inst;
+ /* Combination of MQ_Rotate_XXX bits */
+ u8 rotation;
+ /* 1 if device is active, 0 if poweroff */
+ unsigned active:1;
+ /* 1 if initialization is complete, 0 while it is deferred */
+ unsigned initcomplete:1;
+ /* 1 if power is enabled to the MEDIAQ_11XX_FB_DEVICE_ID subdevice */
+ unsigned poweron:1;
+};
+#define to_mq1100fb_info(n) container_of(n, struct mq1100fb_info, fb)
+
+#define MAX_MQFB_INSTANCES 8
+
+static int ppm [MAX_MQFB_INSTANCES];
+MODULE_PARM(ppm, "i");
+MODULE_PARM_DESC(ppm, "LCD pixel density in pixels per meter");
+
+/* ------------------- chipset specific functions -------------------------- */
+
+static void mq1100fb_power (struct mq1100fb_info *info, int val)
+{
+ debug_func ("val:%d\n", val);
+
+ info->active = (val == 0) ? 1 : 0;
+
+ if (info->active != info->poweron) {
+ info->poweron = info->active;
+ info->base->set_power (info->base, MEDIAQ_11XX_FB_DEVICE_ID,
+ info->active);
+ }
+}
+
+static void mq1100fb_update_screeninfo (struct mq1100fb_info *info, int ppm)
+{
+ u32 control = info->base->regs->GC.control;
+ u32 horizontal_width = info->base->regs->GC.horizontal_window;
+ u32 vertical_height = info->base->regs->GC.vertical_window;
+ u32 window_stride = info->base->regs->GC.window_stride;
+ int stride;
+
+ debug_func ("ppm:%d\n", ppm);
+
+ info->fb.var.grayscale = 0;
+
+ switch (control & MQ_GC_DEPTH) {
+ case MQ_GC_DEPTH_PSEUDO_1:
+ info->fb.var.bits_per_pixel = 1;
+ info->fb.fix.visual = FB_VISUAL_MONO01;
+ break;
+ case MQ_GC_DEPTH_PSEUDO_2:
+ info->fb.var.bits_per_pixel = 2;
+ info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
+ break;
+ case MQ_GC_DEPTH_PSEUDO_4:
+ info->fb.var.bits_per_pixel = 4;
+ info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
+ break;
+ case MQ_GC_DEPTH_PSEUDO_8:
+ info->fb.var.bits_per_pixel = 8;
+ info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
+ break;
+ case MQ_GC_DEPTH_GRAY_1:
+ info->fb.var.bits_per_pixel = 1;
+ info->fb.var.grayscale = 1;
+ info->fb.fix.visual = FB_VISUAL_MONO01;
+ break;
+ case MQ_GC_DEPTH_GRAY_2:
+ info->fb.var.bits_per_pixel = 2;
+ info->fb.var.grayscale = 1;
+ info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
+ break;
+ case MQ_GC_DEPTH_GRAY_4:
+ info->fb.var.bits_per_pixel = 4;
+ info->fb.var.grayscale = 1;
+ info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
+ break;
+ case MQ_GC_DEPTH_GRAY_8:
+ info->fb.var.bits_per_pixel = 8;
+ info->fb.var.grayscale = 1;
+ info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
+ break;
+ case MQ_GC_DEPTH_TRUE_16:
+ info->fb.var.bits_per_pixel = 16;
+ info->fb.fix.visual = FB_VISUAL_TRUECOLOR;
+ break;
+ }
+
+ info->fb.var.xres = info->fb.var.xres_virtual =
+ ((horizontal_width & MQ_GC_HORIZONTAL_WINDOW_WIDTH) >> 16) + 1;
+ info->fb.var.yres = info->fb.var.yres_virtual =
+ ((vertical_height & MQ_GC_VERTICAL_WINDOW_HEIGHT) >> 16) + 1;
+ stride = (short)window_stride;
+ info->fb.fix.line_length = (stride < 0) ? -stride : stride;
+
+ switch (control & (MQ_GC_X_SCANNING_DIRECTION|MQ_GC_LINE_SCANNING_DIRECTION)) {
+ case 0:
+ if (stride >= 0)
+ info->rotation = MQ_Rotate_0; /* 000 */
+ else
+ info->rotation |= MQ_Rotate_0 | MQ_Reflect_Y; /* 010 */
+ break;
+ case MQ_GC_X_SCANNING_DIRECTION:
+ if (stride >= 0)
+ info->rotation = MQ_Rotate_0 | MQ_Reflect_X; /* 001 */
+ else
+ info->rotation = MQ_Rotate_180; /* 011 */
+ break;
+ case MQ_GC_LINE_SCANNING_DIRECTION:
+ if (stride >= 0)
+ info->rotation = MQ_Rotate_90 | MQ_Reflect_X; /* 100 */
+ else
+ info->rotation = MQ_Rotate_90; /* 110 */
+ break;
+ case MQ_GC_LINE_SCANNING_DIRECTION|MQ_GC_X_SCANNING_DIRECTION:
+ if (stride >= 0)
+ info->rotation = MQ_Rotate_270; /* 101 */
+ else
+ info->rotation = MQ_Rotate_270 | MQ_Reflect_X; /* 111 */
+ break;
+ }
+
+ info->fb.var.width = info->fb.var.xres * 1000 / ppm;
+ info->fb.var.height = info->fb.var.yres * 1000 / ppm;
+}
+
+/*
+ * mq1100fb_check_var():
+ * Round up in the following order: bits_per_pixel, xres,
+ * yres, xres_virtual, yres_virtual, xoffset, yoffset, grayscale,
+ * bitfields, horizontal timing, vertical timing.
+ */
+static int mq1100fb_check_var(struct fb_var_screeninfo *var,
+ struct fb_info *fbinfo)
+{
+ debug_func ("\n");
+
+ switch (var->bits_per_pixel) {
+ case 8:
+ var->red.offset = 0;
+ var->green.offset = 0;
+ var->blue.offset = 0;
+ var->red.length = 6;
+ var->green.length = 6;
+ var->blue.length = 6;
+ break;
+ case 16:
+ var->red.offset = 11;
+ var->green.offset = 5;
+ var->blue.offset = 0;
+ var->red.length = 5;
+ var->green.length = 6;
+ var->blue.length = 5;
+ break;
+ default:
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+static int mq1100fb_set_par(struct fb_info *fbinfo)
+{
+ struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
+
+ debug_func ("\n");
+
+ if (!info->active)
+ /* Enable the LCD controller */
+ mq1100fb_power (info, 0);
+
+ return 0;
+}
+
+static int mq1100fb_setcolreg(unsigned regno, unsigned red, unsigned green,
+ unsigned blue, unsigned transp,
+ struct fb_info *fbinfo)
+{
+ struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
+ int bpp, m = 0;
+
+ debug_func ("color:%d rgba:%d/%d/%d/%d\n",
+ regno, red>>8, green>>8, blue>>8, transp>>8);
+
+ bpp = info->fb.var.bits_per_pixel;
+ m = (bpp <= 8) ? (1 << bpp) : 256;
+ if (regno >= m) {
+ debug ("regno %d out of range (max %d)\n", regno, m);
+ return -EINVAL;
+ }
+
+ info->palette[regno].red = red;
+ info->palette[regno].green = green;
+ info->palette[regno].blue = blue;
+ info->palette[regno].transp = transp;
+
+ switch (bpp) {
+ case 8:
+ break;
+ case 16:
+ /* RGB 565 */
+ info->pseudo_pal[regno] = ((red & 0xF800) |
+ ((green & 0xFC00) >> 5) |
+ ((blue & 0xF800) >> 11));
+ break;
+ }
+
+ return 0;
+}
+
+static int mq1100fb_pan_display(struct fb_var_screeninfo *var,
+ struct fb_info *fbinfo)
+{
+ debug_func ("\n");
+ /*
+ * Pan (or wrap, depending on the `vmode' field) the display using the
+ * `xoffset' and `yoffset' fields of the `var' structure.
+ * If the values don't fit, return -EINVAL.
+ */
+
+ /* ... */
+ return 0;
+}
+
+static void mq1100fb_rotate (struct fb_info *fbinfo, int angle)
+{
+ /* For now it is not implemented but mq1100 fully
+ * supports display rotation.
+ */
+ debug_func ("\n");
+}
+
+static int mq1100fb_blank(int blank_mode, struct fb_info *fbinfo)
+{
+ struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
+
+ debug_func ("blank_mode:%d\n", blank_mode);
+
+ /*
+ * Blank the screen if blank_mode != 0, else unblank. If blank == NULL
+ * then the caller blanks by setting the CLUT (Color Look Up Table) to all
+ * black. Return 0 if blanking succeeded, != 0 if un-/blanking failed due
+ * to e.g. a video mode which doesn't support it. Implements VESA suspend
+ * and powerdown modes on hardware that supports disabling hsync/vsync:
+ * blank_mode == 2: suspend vsync
+ * blank_mode == 3: suspend hsync
+ * blank_mode == 4: powerdown
+ */
+
+ mq1100fb_power (info, blank_mode);
+
+ return 0;
+}
+
+/* ------------ Interfaces to hardware functions ------------ */
+
+static struct fb_ops mq1100fb_ops = {
+ .owner = THIS_MODULE,
+ .fb_check_var = mq1100fb_check_var,
+ .fb_set_par = mq1100fb_set_par,
+ .fb_setcolreg = mq1100fb_setcolreg,
+ .fb_fillrect = cfb_fillrect,
+ .fb_copyarea = cfb_copyarea,
+ .fb_imageblit = cfb_imageblit,
+ .fb_blank = mq1100fb_blank,
+ .fb_pan_display = mq1100fb_pan_display,
+ .fb_rotate = mq1100fb_rotate,
+ .fb_cursor = soft_cursor
+};
+
+static struct fb_bitfield def_rgb [3] = {
+ { 11, 5, 0 }, /* red */
+ { 5, 6, 0 }, /* green */
+ { 0, 5, 0 }, /* blue */
+};
+
+static int mq1100fb_finish_init (struct mq1100fb_info *info)
+{
+ int err;
+ int inst_ppm = ppm [info->inst];
+ if (!inst_ppm)
+ inst_ppm = 4210;
+
+ debug_func ("\n");
+
+ info->fb.var.red = def_rgb [0];
+ info->fb.var.green = def_rgb [1];
+ info->fb.var.blue = def_rgb [2];
+ info->fb.var.activate = FB_ACTIVATE_NOW;
+
+ strcpy (info->fb.fix.id, "mq1100");
+ info->fb.fix.type = FB_TYPE_PACKED_PIXELS;
+ info->fb.fix.type_aux = 0;
+ info->fb.fix.xpanstep = info->fb.fix.ypanstep = 0;
+ info->fb.fix.ywrapstep = 0;
+ info->fb.fix.accel = FB_ACCEL_NONE;
+
+ info->fb.screen_base = info->base->gfxram;
+ info->fb.pseudo_palette = &info->pseudo_pal;
+ info->fb.fbops = &mq1100fb_ops;
+
+ mq1100fb_update_screeninfo (info, inst_ppm);
+
+ info->fb_size = info->fb.fix.line_length * info->fb.var.yres_virtual;
+ info->fb_addr = info->base->alloc (info->base, info->fb_size, 1);
+
+ if (info->fb_addr == (u32)-1) {
+ err = -ENOMEM;
+ printk (KERN_ERR "Cannot allocate %u bytes in MediaQ internal RAM for framebuffer\n",
+ info->fb_size);
+error: kfree (info);
+ return err;
+ }
+
+ //info->fb.fix.mmio_start = info->base->paddr_regs;
+ //info->fb.fix.mmio_len = MQ11xx_REG_SIZE;
+ info->fb.fix.smem_start = info->base->paddr_gfxram + info->fb_addr;
+ info->fb.fix.smem_len = info->fb_size;
+
+ /* Program framebuffer start address */
+ info->base->regs->GC.window_start_address = info->fb_addr;
+
+ if ((err = register_framebuffer(&info->fb)) < 0) {
+ printk (KERN_ERR "Could not register mq1100 framebuffer\n");
+ info->base->free (info->base, info->fb_addr, info->fb_size);
+ goto error;
+ }
+
+ info->initcomplete = 1;
+
+ /* Clear the screen in the case we don't use fbcon */
+ memset (info->base->gfxram + info->fb_addr, 0, info->fb_size);
+
+ debug ("frame buffer device %dx%d-%dbpp\n",
+ info->fb.var.xres, info->fb.var.yres, info->fb.var.bits_per_pixel);
+ return 0;
+}
+
+static int mq1100fb_probe (struct device *dev, struct mediaq11xx_base *base)
+{
+ struct platform_device *pdev = to_platform_device(dev);
+ struct mq1100fb_info *info;
+
+ info = kmalloc (sizeof (struct mq1100fb_info), GFP_KERNEL);
+ memset (info, 0, sizeof (struct mq1100fb_info));
+ info->base = base;
+ info->inst = pdev->id;
+
+ dev_set_drvdata (dev, info);
+
+ /* Turn on the power to the MediaQ chip */
+ mq1100fb_power (info, 0);
+ mq1100fb_finish_init (info);
+
+ return 0;
+}
+
+static int mq1100fb_platform_probe (struct device *dev)
+{
+ debug_func ("\n");
+ return mq1100fb_probe (dev, (struct mediaq11xx_base *)dev->platform_data);
+}
+
+static int mq1100fb_platform_remove (struct device *dev)
+{
+ struct mq1100fb_info *info =
+ (struct mq1100fb_info *)dev_get_drvdata (dev);
+
+ debug_func ("\n");
+
+ if (info->active) {
+ mq1100fb_power (info, 4);
+ unregister_framebuffer (&info->fb);
+ info->base->free (info->base, info->fb_addr, info->fb_size);
+ }
+
+ return 0;
+}
+
+static int mq1100fb_platform_suspend (struct device *dev, u32 state, u32 level)
+{
+ struct mq1100fb_info *info =
+ (struct mq1100fb_info *)dev_get_drvdata (dev);
+
+ debug_func ("\n");
+
+ mq1100fb_power (info, 4);
+
+ return 0;
+}
+
+static int mq1100fb_platform_resume (struct device *dev, u32 level)
+{
+ struct mq1100fb_info *info =
+ (struct mq1100fb_info *)dev_get_drvdata (dev);
+
+ debug_func ("\n");
+
+ mq1100fb_power (info, 0);
+
+ return 0;
+}
+
+/* We need the framebuffer subdevice */
+struct device_driver mq1100fb_device_driver = {
+ .name = "mq11xx_fb",
+ .bus = &platform_bus_type,
+ .probe = mq1100fb_platform_probe,
+ .remove = mq1100fb_platform_remove,
+ .suspend = mq1100fb_platform_suspend,
+ .resume = mq1100fb_platform_resume
+};
+
+static int __init mq1100fb_init(void)
+{
+ return driver_register (&mq1100fb_device_driver);
+}
+
+static void __exit mq1100fb_exit(void)
+{
+ driver_unregister (&mq1100fb_device_driver);
+}
+
+module_init(mq1100fb_init);
+module_exit(mq1100fb_exit);
+
+MODULE_AUTHOR("Keith Packard <keithp@keithp.com>");
+MODULE_DESCRIPTION("Framebuffer driver for MediaQ 1100/32/68/78/88 chips");
+MODULE_LICENSE("GPL");
_
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 7:18 framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree akpm
@ 2005-08-05 9:47 ` Andrey Volkov
2005-08-05 20:06 ` James Simmons
2005-08-05 14:08 ` Alexey Dobriyan
` (2 subsequent siblings)
3 siblings, 1 reply; 8+ messages in thread
From: Andrey Volkov @ 2005-08-05 9:47 UTC (permalink / raw)
To: linux-fbdev-devel; +Cc: jamey, anpaza, mm-commits
akpm@osdl.org wrote:
> + *
> + * keithp@keithp.com
> + *
> + * ChangeLog
> + *
> + * 2003-12-06: Andrew Zabolotny <zap@homelink.ru>
> + * - Modified to use the MediaQ SoC base driver to allow
> + * sharing of other MediaQ subdevices with other drivers.
> + * 2003-05-18: <keithp@keithp.com>
> + * - Ported from PCI development board to ARM H5400
> + */
> +
> +#include <linux/module.h>
> +#include <linux/kernel.h>
> +#include <linux/errno.h>
> +#include <linux/string.h>
> +#include <linux/fb.h>
> +#include <linux/init.h>
> +#include <linux/device.h>
> +#include <linux/notifier.h>
> +#include <../drivers/platform/mq11xx.h>
^^^^^^^^^^^^^^^^^
Andrey, Jamey, please, move platform driver
from drivers/platform to drivers/mfd.
--
Regards
Andrey Volkov
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 7:18 framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree akpm
2005-08-05 9:47 ` Andrey Volkov
@ 2005-08-05 14:08 ` Alexey Dobriyan
2005-08-05 20:08 ` James Simmons
2005-08-05 20:15 ` James Simmons
2005-08-07 10:11 ` Antonino A. Daplas
3 siblings, 1 reply; 8+ messages in thread
From: Alexey Dobriyan @ 2005-08-05 14:08 UTC (permalink / raw)
To: jamey; +Cc: anpaza, linux-fbdev-devel, akpm
On Fri, Aug 05, 2005 at 12:18:29AM -0700, akpm@osdl.org wrote:
> This patch adds a framebuffer driver for MQ11xx system-on-chip graphics
> chip. This chip is used in several non-PCI ARM and MIPS platforms such as
> the iPAQ H5550. This driver depends on the overall platform_device driver
> for the chip.
> --- /dev/null
> +++ devel-akpm/drivers/video/mq1100fb.c
> + * linux/drivers/mq1100fb.c
Not true.
> +static int mq1100fb_probe (struct device *dev, struct mediaq11xx_base *base)
> +{
> + info = kmalloc (sizeof (struct mq1100fb_info), GFP_KERNEL);
> + memset (info, 0, sizeof (struct mq1100fb_info));
Unchecked kmalloc().
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 9:47 ` Andrey Volkov
@ 2005-08-05 20:06 ` James Simmons
2005-08-06 9:54 ` [Linux-fbdev-devel] " Andrew Zabolotny
0 siblings, 1 reply; 8+ messages in thread
From: James Simmons @ 2005-08-05 20:06 UTC (permalink / raw)
To: linux-fbdev-devel; +Cc: jamey, anpaza, mm-commits
> > + * keithp@keithp.com
> > + *
> > + * ChangeLog
> > + *
> > + * 2003-12-06: Andrew Zabolotny <zap@homelink.ru>
> > + * - Modified to use the MediaQ SoC base driver to allow
> > + * sharing of other MediaQ subdevices with other drivers.
> > + * 2003-05-18: <keithp@keithp.com>
> > + * - Ported from PCI development board to ARM H5400
> > + */
> > +
> > +#include <linux/module.h>
> > +#include <linux/kernel.h>
> > +#include <linux/errno.h>
> > +#include <linux/string.h>
> > +#include <linux/fb.h>
> > +#include <linux/init.h>
> > +#include <linux/device.h>
> > +#include <linux/notifier.h>
> > +#include <../drivers/platform/mq11xx.h>
> ^^^^^^^^^^^^^^^^^
> Andrey, Jamey, please, move platform driver
> from drivers/platform to drivers/mfd.
I don't see the mq11xx.h. If it contains graphics related
information like register names I would recommend
it being placed into include/video.
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: Re: framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 14:08 ` Alexey Dobriyan
@ 2005-08-05 20:08 ` James Simmons
0 siblings, 0 replies; 8+ messages in thread
From: James Simmons @ 2005-08-05 20:08 UTC (permalink / raw)
To: linux-fbdev-devel; +Cc: jamey, anpaza, akpm
> > +static int mq1100fb_probe (struct device *dev, struct mediaq11xx_base *base)
> > +{
>
> > + info = kmalloc (sizeof (struct mq1100fb_info), GFP_KERNEL);
> > + memset (info, 0, sizeof (struct mq1100fb_info));
>
> Unchecked kmalloc().
Please use the framebuffer_alloc and framebuffer_release api in fbsysfs.c.
Otherwise your driver wil not show up in the sysfs filesystem.
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 7:18 framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree akpm
2005-08-05 9:47 ` Andrey Volkov
2005-08-05 14:08 ` Alexey Dobriyan
@ 2005-08-05 20:15 ` James Simmons
2005-08-07 10:11 ` Antonino A. Daplas
3 siblings, 0 replies; 8+ messages in thread
From: James Simmons @ 2005-08-05 20:15 UTC (permalink / raw)
To: linux-fbdev-devel; +Cc: jamey, anpaza, mm-commits
> +struct mq1100fb_info {
> + /* Framebuffer info */
> + struct fb_info fb;
> + /* The link to the base SoC driver */
> + struct mediaq11xx_base *base;
> + /* The RGB palette */
> + struct mq1100fb_rgb palette[256];
> + /* Notifier block */
> + struct notifier_block notify;
> + /* Framebuffer offset inside MediaQ RAM */
> + u32 fb_addr, fb_size;
> + /* The pseudo-palette */
> + u32 pseudo_pal[16];
> + /* Device instance number (0-7) */
> + u8 inst;
> + /* Combination of MQ_Rotate_XXX bits */
> + u8 rotation;
> + /* 1 if device is active, 0 if poweroff */
> + unsigned active:1;
> + /* 1 if initialization is complete, 0 while it is deferred */
> + unsigned initcomplete:1;
> + /* 1 if power is enabled to the MEDIAQ_11XX_FB_DEVICE_ID subdevice */
> + unsigned poweron:1;
> +};
I recommend you rename that to mq1100_par and remove the struct fb_info in
there. Its easier to deal with when you will use framebuffer_alloc.
> +static int mq1100fb_probe (struct device *dev, struct mediaq11xx_base *base)
> +{
> + struct platform_device *pdev = to_platform_device(dev);
> + struct fb_info *info;
> +
> + info = kmalloc (sizeof (struct mq1100fb_info), GFP_KERNEL);
> + memset (info, 0, sizeof (struct mq1100fb_info));
info = framebuffer_alloc(sizeof(struct mq1100_par), &pdev->dev);
> +static int mq1100fb_platform_remove (struct device *dev)
> +{
> + struct fb_info *info =
> + (struct fb_info *)dev_get_drvdata (dev);
> +
> + debug_func ("\n");
> +
> + if (info->active) {
> + mq1100fb_power (info, 4);
> + unregister_framebuffer (&info->fb);
> + info->base->free (info->base, info->fb_addr, info->fb_size);
> + }
framebuffer_release(info);
> + return 0;
> +}
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Linux-fbdev-devel] framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 20:06 ` James Simmons
@ 2005-08-06 9:54 ` Andrew Zabolotny
0 siblings, 0 replies; 8+ messages in thread
From: Andrew Zabolotny @ 2005-08-06 9:54 UTC (permalink / raw)
To: James Simmons; +Cc: linux-fbdev-devel, jamey, anpaza, mm-commits
On Fri, 5 Aug 2005 21:06:17 +0100 (BST)
James Simmons <jsimmons@infradead.org> wrote:
> I don't see the mq11xx.h. If it contains graphics related
> information like register names I would recommend
> it being placed into include/video.
mq11xx.h contains register names, but its not framebuffer-specific
because this chip contains several functions inside, like an USB Device
Controller (UDC), an SPI controller, an auxiliary GPIO controller and
more. Maybe it should be in include/mfd if the .c file will be moved to
drivers/mfd.
--
Greetings,
Andrew
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree
2005-08-05 7:18 framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree akpm
` (2 preceding siblings ...)
2005-08-05 20:15 ` James Simmons
@ 2005-08-07 10:11 ` Antonino A. Daplas
3 siblings, 0 replies; 8+ messages in thread
From: Antonino A. Daplas @ 2005-08-07 10:11 UTC (permalink / raw)
To: linux-fbdev-devel; +Cc: jamey, anpaza, mm-commits
akpm@osdl.org wrote:
> The patch titled
>
> framebuffer driver for MQ11xx graphics chip
>
> has been added to the -mm tree. Its filename is
>
> framebuffer-driver-for-mq11xx-graphics-chip.patch
>
> Patches currently in -mm which might be from jamey@handhelds.org are
>
> platform-device-driver-for-mq11xx-graphics-chip.patch
> framebuffer-driver-for-mq11xx-graphics-chip.patch
> usb-gadget-driver-for-mq11xx-graphics-chip.patch
>
>
>
> From: Jamey Hicks <jamey@handhelds.org>
>
> This patch adds a framebuffer driver for MQ11xx system-on-chip graphics
> chip. This chip is used in several non-PCI ARM and MIPS platforms such as
> the iPAQ H5550. This driver depends on the overall platform_device driver
> for the chip.
>
> Signed-off-by: Jamey Hicks <jamey@handhelds.org>
> Signed-off-by: Andrew Zabolotny <anpaza@mail.ru>
> Cc: <linux-fbdev-devel@lists.sourceforge.net>
> Signed-off-by: Andrew Morton <akpm@osdl.org>
> ---
>
> drivers/video/Kconfig | 17 +
> drivers/video/Makefile | 1
> drivers/video/mq1100fb.c | 497 +++++++++++++++++++++++++++++++++++++++++++++++
> 3 files changed, 515 insertions(+)
>
> diff -puN drivers/video/Kconfig~framebuffer-driver-for-mq11xx-graphics-chip drivers/video/Kconfig
> --- devel/drivers/video/Kconfig~framebuffer-driver-for-mq11xx-graphics-chip 2005-08-05 00:18:05.000000000 -0700
> +++ devel-akpm/drivers/video/Kconfig 2005-08-05 00:18:05.000000000 -0700
> @@ -1438,6 +1438,23 @@ config FB_PXA
>
> If unsure, say N.
>
> +config FB_MQ1100
> + tristate "MQ1100/32/68/78/88 framebuffer support"
> + depends on FB && PLATFORM_MQ11XX
> + select FB_CFB_FILLRECT
> + select FB_CFB_COPYAREA
> + select FB_CFB_IMAGEBLIT
> + select FB_SOFT_CURSOR
> + help
> + This is a framebuffer device for the MediaQ 1100/32/68/78/88
> + LCD controllers (http://www.mediaq.com) found in some PDAs
> + (these include: iPAQ 5400, Axim X5, iPAQ 221x).
> +
> + This driver handles only the LCD controller apect of the MediaQ;
> + other functions are handled in respective drivers.
> + See <http://www.linux-fbdev.org/> for information
> + on framebuffer devices.
> +
> config FB_W100
> tristate "W100 frame buffer support"
> depends on FB && PXA_SHARPSL
> diff -puN drivers/video/Makefile~framebuffer-driver-for-mq11xx-graphics-chip drivers/video/Makefile
> --- devel/drivers/video/Makefile~framebuffer-driver-for-mq11xx-graphics-chip 2005-08-05 00:18:05.000000000 -0700
> +++ devel-akpm/drivers/video/Makefile 2005-08-05 00:18:05.000000000 -0700
> @@ -83,6 +83,7 @@ obj-$(CONFIG_FB_GBE) += gbe
> obj-$(CONFIG_FB_CIRRUS) += cirrusfb.o
> obj-$(CONFIG_FB_ASILIANT) += asiliantfb.o
> obj-$(CONFIG_FB_PXA) += pxafb.o
> +obj-$(CONFIG_FB_MQ1100) += mq1100fb.o
> obj-$(CONFIG_FB_W100) += w100fb.o
> obj-$(CONFIG_FB_AU1100) += au1100fb.o fbgen.o
> obj-$(CONFIG_FB_PMAG_AA) += pmag-aa-fb.o
> diff -puN /dev/null drivers/video/mq1100fb.c
> --- /dev/null 2003-09-15 06:40:47.000000000 -0700
> +++ devel-akpm/drivers/video/mq1100fb.c 2005-08-05 00:18:05.000000000 -0700
> @@ -0,0 +1,497 @@
> +/*
> + * linux/drivers/mq1100fb.c
> + *
> + * Copyright © 2003 Keith Packard
> + *
> + * 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.
> + *
> + * MediaQ 1100/32/68/78/88 LCD Controller Frame Buffer Driver
> + *
> + * Please direct your questions and comments on this driver to the following
> + * email address:
> + *
> + * keithp@keithp.com
> + *
> + * ChangeLog
> + *
> + * 2003-12-06: Andrew Zabolotny <zap@homelink.ru>
> + * - Modified to use the MediaQ SoC base driver to allow
> + * sharing of other MediaQ subdevices with other drivers.
> + * 2003-05-18: <keithp@keithp.com>
> + * - Ported from PCI development board to ARM H5400
> + */
> +
> +#include <linux/module.h>
> +#include <linux/kernel.h>
> +#include <linux/errno.h>
> +#include <linux/string.h>
> +#include <linux/fb.h>
> +#include <linux/init.h>
> +#include <linux/device.h>
> +#include <linux/notifier.h>
> +#include <../drivers/platform/mq11xx.h>
> +
> +#if 0
> +# define debug(s, args...) printk (KERN_INFO s, ##args)
> +#else
> +# define debug(s, args...)
> +#endif
> +#define debug_func(s, args...) debug ("%s: " s, __FUNCTION__, ##args)
> +
> +#define MQ_Rotate_0 1
> +#define MQ_Rotate_90 2
> +#define MQ_Rotate_180 4
> +#define MQ_Rotate_270 8
> +
> +#define MQ_Reflect_X 16
> +#define MQ_Reflect_Y 32
> +
> +struct mq1100fb_rgb {
> + unsigned char red,green,blue,transp;
> +};
> +
> +struct mq1100fb_info {
> + /* Framebuffer info */
> + struct fb_info fb;
If you use framebuffer_alloc(), you need not include
struct fb_info in mq1100fb_info.
> + /* The link to the base SoC driver */
> + struct mediaq11xx_base *base;
> + /* The RGB palette */
> + struct mq1100fb_rgb palette[256];
> + /* Notifier block */
> + struct notifier_block notify;
> + /* Framebuffer offset inside MediaQ RAM */
> + u32 fb_addr, fb_size;
> + /* The pseudo-palette */
> + u32 pseudo_pal[16];
> + /* Device instance number (0-7) */
> + u8 inst;
> + /* Combination of MQ_Rotate_XXX bits */
> + u8 rotation;
> + /* 1 if device is active, 0 if poweroff */
> + unsigned active:1;
> + /* 1 if initialization is complete, 0 while it is deferred */
> + unsigned initcomplete:1;
> + /* 1 if power is enabled to the MEDIAQ_11XX_FB_DEVICE_ID subdevice */
> + unsigned poweron:1;
> +};
> +#define to_mq1100fb_info(n) container_of(n, struct mq1100fb_info, fb)
> +
> +#define MAX_MQFB_INSTANCES 8
> +
> +static int ppm [MAX_MQFB_INSTANCES];
> +MODULE_PARM(ppm, "i");
> +MODULE_PARM_DESC(ppm, "LCD pixel density in pixels per meter");
> +
> +/* ------------------- chipset specific functions -------------------------- */
> +
> +static void mq1100fb_power (struct mq1100fb_info *info, int val)
> +{
> + debug_func ("val:%d\n", val);
> +
> + info->active = (val == 0) ? 1 : 0;
> +
> + if (info->active != info->poweron) {
> + info->poweron = info->active;
> + info->base->set_power (info->base, MEDIAQ_11XX_FB_DEVICE_ID,
> + info->active);
> + }
> +}
> +
> +static void mq1100fb_update_screeninfo (struct mq1100fb_info *info, int ppm)
> +{
> + u32 control = info->base->regs->GC.control;
> + u32 horizontal_width = info->base->regs->GC.horizontal_window;
> + u32 vertical_height = info->base->regs->GC.vertical_window;
> + u32 window_stride = info->base->regs->GC.window_stride;
> + int stride;
> +
> + debug_func ("ppm:%d\n", ppm);
> +
> + info->fb.var.grayscale = 0;
> +
> + switch (control & MQ_GC_DEPTH) {
> + case MQ_GC_DEPTH_PSEUDO_1:
> + info->fb.var.bits_per_pixel = 1;
> + info->fb.fix.visual = FB_VISUAL_MONO01;
> + break;
> + case MQ_GC_DEPTH_PSEUDO_2:
> + info->fb.var.bits_per_pixel = 2;
> + info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
> + break;
> + case MQ_GC_DEPTH_PSEUDO_4:
> + info->fb.var.bits_per_pixel = 4;
> + info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
> + break;
> + case MQ_GC_DEPTH_PSEUDO_8:
> + info->fb.var.bits_per_pixel = 8;
> + info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
> + break;
> + case MQ_GC_DEPTH_GRAY_1:
> + info->fb.var.bits_per_pixel = 1;
> + info->fb.var.grayscale = 1;
> + info->fb.fix.visual = FB_VISUAL_MONO01;
> + break;
> + case MQ_GC_DEPTH_GRAY_2:
> + info->fb.var.bits_per_pixel = 2;
> + info->fb.var.grayscale = 1;
> + info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
> + break;
> + case MQ_GC_DEPTH_GRAY_4:
> + info->fb.var.bits_per_pixel = 4;
> + info->fb.var.grayscale = 1;
> + info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
> + break;
> + case MQ_GC_DEPTH_GRAY_8:
> + info->fb.var.bits_per_pixel = 8;
> + info->fb.var.grayscale = 1;
> + info->fb.fix.visual = FB_VISUAL_PSEUDOCOLOR;
> + break;
> + case MQ_GC_DEPTH_TRUE_16:
> + info->fb.var.bits_per_pixel = 16;
> + info->fb.fix.visual = FB_VISUAL_TRUECOLOR;
> + break;
> + }
> +
> + info->fb.var.xres = info->fb.var.xres_virtual =
> + ((horizontal_width & MQ_GC_HORIZONTAL_WINDOW_WIDTH) >> 16) + 1;
> + info->fb.var.yres = info->fb.var.yres_virtual =
> + ((vertical_height & MQ_GC_VERTICAL_WINDOW_HEIGHT) >> 16) + 1;
> + stride = (short)window_stride;
> + info->fb.fix.line_length = (stride < 0) ? -stride : stride;
> +
> + switch (control & (MQ_GC_X_SCANNING_DIRECTION|MQ_GC_LINE_SCANNING_DIRECTION)) {
> + case 0:
> + if (stride >= 0)
> + info->rotation = MQ_Rotate_0; /* 000 */
> + else
> + info->rotation |= MQ_Rotate_0 | MQ_Reflect_Y; /* 010 */
> + break;
> + case MQ_GC_X_SCANNING_DIRECTION:
> + if (stride >= 0)
> + info->rotation = MQ_Rotate_0 | MQ_Reflect_X; /* 001 */
> + else
> + info->rotation = MQ_Rotate_180; /* 011 */
> + break;
> + case MQ_GC_LINE_SCANNING_DIRECTION:
> + if (stride >= 0)
> + info->rotation = MQ_Rotate_90 | MQ_Reflect_X; /* 100 */
> + else
> + info->rotation = MQ_Rotate_90; /* 110 */
> + break;
> + case MQ_GC_LINE_SCANNING_DIRECTION|MQ_GC_X_SCANNING_DIRECTION:
> + if (stride >= 0)
> + info->rotation = MQ_Rotate_270; /* 101 */
> + else
> + info->rotation = MQ_Rotate_270 | MQ_Reflect_X; /* 111 */
> + break;
> + }
> +
> + info->fb.var.width = info->fb.var.xres * 1000 / ppm;
> + info->fb.var.height = info->fb.var.yres * 1000 / ppm;
> +}
> +
> +/*
> + * mq1100fb_check_var():
> + * Round up in the following order: bits_per_pixel, xres,
> + * yres, xres_virtual, yres_virtual, xoffset, yoffset, grayscale,
> + * bitfields, horizontal timing, vertical timing.
> + */
> +static int mq1100fb_check_var(struct fb_var_screeninfo *var,
> + struct fb_info *fbinfo)
> +{
> + debug_func ("\n");
> +
> + switch (var->bits_per_pixel) {
> + case 8:
> + var->red.offset = 0;
> + var->green.offset = 0;
> + var->blue.offset = 0;
> + var->red.length = 6;
> + var->green.length = 6;
> + var->blue.length = 6;
> + break;
> + case 16:
> + var->red.offset = 11;
> + var->green.offset = 5;
> + var->blue.offset = 0;
> + var->red.length = 5;
> + var->green.length = 6;
> + var->blue.length = 5;
> + break;
> + default:
> + return -EINVAL;
> + }
> +
> + return 0;
> +}
> +
> +static int mq1100fb_set_par(struct fb_info *fbinfo)
> +{
> + struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
> +
> + debug_func ("\n");
> +
> + if (!info->active)
> + /* Enable the LCD controller */
> + mq1100fb_power (info, 0);
> +
> + return 0;
> +}
> +
> +static int mq1100fb_setcolreg(unsigned regno, unsigned red, unsigned green,
> + unsigned blue, unsigned transp,
> + struct fb_info *fbinfo)
> +{
> + struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
> + int bpp, m = 0;
> +
> + debug_func ("color:%d rgba:%d/%d/%d/%d\n",
> + regno, red>>8, green>>8, blue>>8, transp>>8);
> +
> + bpp = info->fb.var.bits_per_pixel;
> + m = (bpp <= 8) ? (1 << bpp) : 256;
> + if (regno >= m) {
> + debug ("regno %d out of range (max %d)\n", regno, m);
> + return -EINVAL;
> + }
> +
> + info->palette[regno].red = red;
> + info->palette[regno].green = green;
> + info->palette[regno].blue = blue;
> + info->palette[regno].transp = transp;
> +
> + switch (bpp) {
> + case 8:
> + break;
> + case 16:
> + /* RGB 565 */
> + info->pseudo_pal[regno] = ((red & 0xF800) |
> + ((green & 0xFC00) >> 5) |
> + ((blue & 0xF800) >> 11));
> + break;
> + }
> +
> + return 0;
> +}
> +
> +static int mq1100fb_pan_display(struct fb_var_screeninfo *var,
> + struct fb_info *fbinfo)
> +{
> + debug_func ("\n");
> + /*
> + * Pan (or wrap, depending on the `vmode' field) the display using the
> + * `xoffset' and `yoffset' fields of the `var' structure.
> + * If the values don't fit, return -EINVAL.
> + */
> +
> + /* ... */
> + return 0;
> +}
If with no pan_display, just comment out the entire function.
> +
> +static void mq1100fb_rotate (struct fb_info *fbinfo, int angle)
> +{
> + /* For now it is not implemented but mq1100 fully
> + * supports display rotation.
> + */
> + debug_func ("\n");
> +}
> +
> +static int mq1100fb_blank(int blank_mode, struct fb_info *fbinfo)
> +{
> + struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
> +
> + debug_func ("blank_mode:%d\n", blank_mode);
> +
> + /*
> + * Blank the screen if blank_mode != 0, else unblank. If blank == NULL
> + * then the caller blanks by setting the CLUT (Color Look Up Table) to all
> + * black. Return 0 if blanking succeeded, != 0 if un-/blanking failed due
> + * to e.g. a video mode which doesn't support it. Implements VESA suspend
> + * and powerdown modes on hardware that supports disabling hsync/vsync:
> + * blank_mode == 2: suspend vsync
> + * blank_mode == 3: suspend hsync
> + * blank_mode == 4: powerdown
> + */
> +
> + mq1100fb_power (info, blank_mode);
> +
> + return 0;
> +}
> +
> +/* ------------ Interfaces to hardware functions ------------ */
> +
> +static struct fb_ops mq1100fb_ops = {
> + .owner = THIS_MODULE,
> + .fb_check_var = mq1100fb_check_var,
> + .fb_set_par = mq1100fb_set_par,
> + .fb_setcolreg = mq1100fb_setcolreg,
> + .fb_fillrect = cfb_fillrect,
> + .fb_copyarea = cfb_copyarea,
> + .fb_imageblit = cfb_imageblit,
> + .fb_blank = mq1100fb_blank,
> + .fb_pan_display = mq1100fb_pan_display,
> + .fb_rotate = mq1100fb_rotate,
> + .fb_cursor = soft_cursor
> +};
> +
> +static struct fb_bitfield def_rgb [3] = {
> + { 11, 5, 0 }, /* red */
> + { 5, 6, 0 }, /* green */
> + { 0, 5, 0 }, /* blue */
> +};
> +
> +static int mq1100fb_finish_init (struct mq1100fb_info *info)
> +{
> + int err;
> + int inst_ppm = ppm [info->inst];
> + if (!inst_ppm)
> + inst_ppm = 4210;
> +
> + debug_func ("\n");
> +
> + info->fb.var.red = def_rgb [0];
> + info->fb.var.green = def_rgb [1];
> + info->fb.var.blue = def_rgb [2];
> + info->fb.var.activate = FB_ACTIVATE_NOW;
> +
> + strcpy (info->fb.fix.id, "mq1100");
> + info->fb.fix.type = FB_TYPE_PACKED_PIXELS;
> + info->fb.fix.type_aux = 0;
> + info->fb.fix.xpanstep = info->fb.fix.ypanstep = 0;
> + info->fb.fix.ywrapstep = 0;
> + info->fb.fix.accel = FB_ACCEL_NONE;
> +
> + info->fb.screen_base = info->base->gfxram;
> + info->fb.pseudo_palette = &info->pseudo_pal;
> + info->fb.fbops = &mq1100fb_ops;
Don't forget to allocate info->fb.cmap with fb_alloc_cmap(). And
an equivalent fb_dealloc_cmap() on platform_remove.
You might get some hard-to-pinpoint user app bugs.
> +
> + mq1100fb_update_screeninfo (info, inst_ppm);
> +
> + info->fb_size = info->fb.fix.line_length * info->fb.var.yres_virtual;
> + info->fb_addr = info->base->alloc (info->base, info->fb_size, 1);
> +
> + if (info->fb_addr == (u32)-1) {
> + err = -ENOMEM;
> + printk (KERN_ERR "Cannot allocate %u bytes in MediaQ internal RAM for framebuffer\n",
> + info->fb_size);
> +error: kfree (info);
> + return err;
> + }
> +
> + //info->fb.fix.mmio_start = info->base->paddr_regs;
> + //info->fb.fix.mmio_len = MQ11xx_REG_SIZE;
> + info->fb.fix.smem_start = info->base->paddr_gfxram + info->fb_addr;
> + info->fb.fix.smem_len = info->fb_size;
> +
> + /* Program framebuffer start address */
> + info->base->regs->GC.window_start_address = info->fb_addr;
> +
> + if ((err = register_framebuffer(&info->fb)) < 0) {
> + printk (KERN_ERR "Could not register mq1100 framebuffer\n");
> + info->base->free (info->base, info->fb_addr, info->fb_size);
> + goto error;
> + }
> +
> + info->initcomplete = 1;
> +
> + /* Clear the screen in the case we don't use fbcon */
> + memset (info->base->gfxram + info->fb_addr, 0, info->fb_size);
memset_io?
> +
> + debug ("frame buffer device %dx%d-%dbpp\n",
> + info->fb.var.xres, info->fb.var.yres, info->fb.var.bits_per_pixel);
> + return 0;
> +}
> +
> +static int mq1100fb_probe (struct device *dev, struct mediaq11xx_base *base)
> +{
> + struct platform_device *pdev = to_platform_device(dev);
> + struct mq1100fb_info *info;
> +
> + info = kmalloc (sizeof (struct mq1100fb_info), GFP_KERNEL);
Is it possible to use framebuffer_alloc() instead?.
struct fb_info *info = framebuffer_alloc(sizeof(struct mq1100fb_info, dev));
Then instead of below...
struct mq1100fb_info *info = to_mq1100fb_info(fbinfo);
do
struct mq1100fb_info *info = fbinfo->par;
> + memset (info, 0, sizeof (struct mq1100fb_info));
No need to memset if framebuffer_alloc() is used. And check
if kmalloc (framebuffer_alloc()) is successful.
> + info->base = base;
> + info->inst = pdev->id;
> +
> + dev_set_drvdata (dev, info);
> +
> + /* Turn on the power to the MediaQ chip */
> + mq1100fb_power (info, 0);
> + mq1100fb_finish_init (info);
> +
> + return 0;
> +}
> +
> +static int mq1100fb_platform_probe (struct device *dev)
> +{
> + debug_func ("\n");
> + return mq1100fb_probe (dev, (struct mediaq11xx_base *)dev->platform_data);
> +}
> +
> +static int mq1100fb_platform_remove (struct device *dev)
> +{
> + struct mq1100fb_info *info =
> + (struct mq1100fb_info *)dev_get_drvdata (dev);
> +
> + debug_func ("\n");
> +
> + if (info->active) {
> + mq1100fb_power (info, 4);
> + unregister_framebuffer (&info->fb);
> + info->base->free (info->base, info->fb_addr, info->fb_size);
kfree(info)? (Or framebuffer_dealloc() for that matter?)
> + }
> +
> + return 0;
> +}
> +
> +static int mq1100fb_platform_suspend (struct device *dev, u32 state, u32 level)
> +{
> + struct mq1100fb_info *info =
> + (struct mq1100fb_info *)dev_get_drvdata (dev);
> +
> + debug_func ("\n");
> +
> + mq1100fb_power (info, 4);
> +
> + return 0;
> +}
> +
> +static int mq1100fb_platform_resume (struct device *dev, u32 level)
> +{
> + struct mq1100fb_info *info =
> + (struct mq1100fb_info *)dev_get_drvdata (dev);
> +
> + debug_func ("\n");
> +
> + mq1100fb_power (info, 0);
> +
> + return 0;
> +}
> +
> +/* We need the framebuffer subdevice */
> +struct device_driver mq1100fb_device_driver = {
> + .name = "mq11xx_fb",
> + .bus = &platform_bus_type,
> + .probe = mq1100fb_platform_probe,
> + .remove = mq1100fb_platform_remove,
> + .suspend = mq1100fb_platform_suspend,
> + .resume = mq1100fb_platform_resume
> +};
> +
> +static int __init mq1100fb_init(void)
> +{
> + return driver_register (&mq1100fb_device_driver);
> +}
> +
> +static void __exit mq1100fb_exit(void)
> +{
> + driver_unregister (&mq1100fb_device_driver);
> +}
> +
> +module_init(mq1100fb_init);
> +module_exit(mq1100fb_exit);
> +
> +MODULE_AUTHOR("Keith Packard <keithp@keithp.com>");
> +MODULE_DESCRIPTION("Framebuffer driver for MediaQ 1100/32/68/78/88 chips");
> +MODULE_LICENSE("GPL");
> _
>
>
> -------------------------------------------------------
> SF.Net email is Sponsored by the Better Software Conference & EXPO
> September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
> Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
> Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
> _______________________________________________
> Linux-fbdev-devel mailing list
> Linux-fbdev-devel@lists.sourceforge.net
> https://lists.sourceforge.net/lists/listinfo/linux-fbdev-devel
>
-------------------------------------------------------
SF.Net email is Sponsored by the Better Software Conference & EXPO
September 19-22, 2005 * San Francisco, CA * Development Lifecycle Practices
Agile & Plan-Driven Development * Managing Projects & Teams * Testing & QA
Security * Process Improvement & Measurement * http://www.sqe.com/bsce5sf
^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2005-08-07 10:11 UTC | newest]
Thread overview: 8+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2005-08-05 7:18 framebuffer-driver-for-mq11xx-graphics-chip.patch added to -mm tree akpm
2005-08-05 9:47 ` Andrey Volkov
2005-08-05 20:06 ` James Simmons
2005-08-06 9:54 ` [Linux-fbdev-devel] " Andrew Zabolotny
2005-08-05 14:08 ` Alexey Dobriyan
2005-08-05 20:08 ` James Simmons
2005-08-05 20:15 ` James Simmons
2005-08-07 10:11 ` Antonino A. Daplas
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).