summaryrefslogtreecommitdiffstats
path: root/drivers/video
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/video')
-rw-r--r--drivers/video/Config.in89
-rw-r--r--drivers/video/Makefile160
-rw-r--r--drivers/video/S3triofb.c885
-rw-r--r--drivers/video/amifb.c821
-rw-r--r--drivers/video/atafb.c517
-rw-r--r--drivers/video/ati-gt.h203
-rw-r--r--drivers/video/ati-gx.h122
-rw-r--r--drivers/video/ati-vt.h147
-rw-r--r--drivers/video/aty.h923
-rw-r--r--drivers/video/atyfb.c1685
-rw-r--r--drivers/video/cyberfb.c629
-rw-r--r--drivers/video/dnfb.c (renamed from drivers/video/dn_fb.c)161
-rw-r--r--drivers/video/fbcmap.c105
-rw-r--r--drivers/video/fbcon-afb.c399
-rw-r--r--drivers/video/fbcon-afb.h15
-rw-r--r--drivers/video/fbcon-cfb16.c194
-rw-r--r--drivers/video/fbcon-cfb16.h16
-rw-r--r--drivers/video/fbcon-cfb2.c205
-rw-r--r--drivers/video/fbcon-cfb2.h15
-rw-r--r--drivers/video/fbcon-cfb24.c221
-rw-r--r--drivers/video/fbcon-cfb24.h16
-rw-r--r--drivers/video/fbcon-cfb32.c205
-rw-r--r--drivers/video/fbcon-cfb32.h16
-rw-r--r--drivers/video/fbcon-cfb4.c208
-rw-r--r--drivers/video/fbcon-cfb4.h15
-rw-r--r--drivers/video/fbcon-cfb8.c141
-rw-r--r--drivers/video/fbcon-cfb8.h15
-rw-r--r--drivers/video/fbcon-cyber.c229
-rw-r--r--drivers/video/fbcon-ilbm.c137
-rw-r--r--drivers/video/fbcon-ilbm.h15
-rw-r--r--drivers/video/fbcon-iplan2p2.c241
-rw-r--r--drivers/video/fbcon-iplan2p2.h15
-rw-r--r--drivers/video/fbcon-iplan2p4.c262
-rw-r--r--drivers/video/fbcon-iplan2p4.h15
-rw-r--r--drivers/video/fbcon-iplan2p8.c315
-rw-r--r--drivers/video/fbcon-iplan2p8.h15
-rw-r--r--drivers/video/fbcon-mac.c513
-rw-r--r--drivers/video/fbcon-mac.h15
-rw-r--r--drivers/video/fbcon-mfb.c107
-rw-r--r--drivers/video/fbcon-mfb.h15
-rw-r--r--drivers/video/fbcon-retz3.c260
-rw-r--r--drivers/video/fbcon.c571
-rw-r--r--drivers/video/fbcon.h19
-rw-r--r--drivers/video/fbgen.c386
-rw-r--r--drivers/video/font_6x11.c3345
-rw-r--r--drivers/video/fonts.c31
-rw-r--r--drivers/video/macfb.c459
-rw-r--r--drivers/video/offb.c612
-rw-r--r--drivers/video/retz3fb.c567
-rw-r--r--drivers/video/skeletonfb.c388
-rw-r--r--drivers/video/tgafb.c201
-rw-r--r--drivers/video/txtcon.c117
-rw-r--r--drivers/video/vfb.c234
-rw-r--r--drivers/video/vgacon.c116
-rw-r--r--drivers/video/virgefb.c1190
55 files changed, 14726 insertions, 3792 deletions
diff --git a/drivers/video/Config.in b/drivers/video/Config.in
index e39e33bfc..b4766876b 100644
--- a/drivers/video/Config.in
+++ b/drivers/video/Config.in
@@ -7,43 +7,70 @@ if [ "$CONFIG_FB" = "y" ]; then
mainmenu_option next_comment
comment 'Frame buffer devices'
- if [ "$CONFIG_AMIGA" = "y" ]; then
+ if [ "$CONFIG_APOLLO" = "y" ]; then
+ define_bool CONFIG_FB_APOLLO y
+ fi
+ if [ "$CONFIG_AMIGA" = "y" ]; then
bool 'Amiga native chipset support' CONFIG_FB_AMIGA
if [ "$CONFIG_FB_AMIGA" != "n" ]; then
bool 'Amiga OCS chipset support' CONFIG_FB_AMIGA_OCS
bool 'Amiga ECS chipset support' CONFIG_FB_AMIGA_ECS
bool 'Amiga AGA chipset support' CONFIG_FB_AMIGA_AGA
fi
- tristate 'Amiga Cybervision support' CONFIG_FB_CYBER
+ tristate 'Amiga CyberVision support' CONFIG_FB_CYBER
if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
+ bool 'Amiga CyberVision3D support (experimental)' CONFIG_FB_VIRGE
tristate 'Amiga RetinaZ3 support' CONFIG_FB_RETINAZ3
fi
fi
if [ "$CONFIG_ATARI" = "y" ]; then
bool 'Atari native chipset support' CONFIG_FB_ATARI
-# tristate 'Mach64 Frame Buffer support' CONFIG_FB_MACH64
+ bool 'ATI Mach64 display support' CONFIG_FB_ATY
+ fi
+ if [ "$CONFIG_PPC" = "y" ]; then
+ bool 'Open Firmware frame buffer device support' CONFIG_FB_OF
+ bool 'S3 Trio frame buffer device support' CONFIG_FB_S3TRIO
+ if [ "$CONFIG_FB_OF" = "y" ]; then
+# bool 'Apple "control" display support' CONFIG_FB_CONTROL
+# bool 'Apple "platinum" display support' CONFIG_FB_PLATINUM
+# bool 'Apple "valkyrie" display support' CONFIG_FB_VALKYRIE
+ bool 'ATI Mach64 display support' CONFIG_FB_ATY
+# bool 'IMS Twin Turbo display support' CONFIG_FB_IMSTT
+# bool 'Chips 65550 display support' CONFIG_FB_CT65550
+# bool 'S3 Trio display support' CONFIG_FB_S3TRIO
+ fi
+ fi
+ if [ "$CONFIG_MAC" = "y" ]; then
+ define_bool CONFIG_FB_MAC y
+ fi
+ if [ "$CONFIG_TGA_CONSOLE" = "y" ]; then
+ define_bool CONFIG_FB_TGA y
fi
- if [ "$CONFIG_CHRP" = "y" -o "$CONFIG_PMAC" = "y" ]; then
- bool 'Open Firmware frame buffer device support' CONFIG_FB_OPEN_FIRMWARE
- fi
- tristate 'Virtual Frame Buffer support' CONFIG_FB_VIRTUAL
+ tristate 'Virtual Frame Buffer support (ONLY FOR TESTING!)' CONFIG_FB_VIRTUAL
bool 'Advanced low level driver options' CONFIG_FBCON_ADVANCED
if [ "$CONFIG_FBCON_ADVANCED" = "y" ]; then
- tristate 'Monochrome support' CONFIG_FBCON_MFB
- tristate 'Interleaved bitplanes support' CONFIG_FBCON_ILBM
- tristate 'Normal bitplanes support' CONFIG_FBCON_AFB
- tristate 'Atari interleaved bitplanes (2 planes) support' CONFIG_FBCON_IPLAN2P2
- tristate 'Atari interleaved bitplanes (4 planes) support' CONFIG_FBCON_IPLAN2P4
- tristate 'Atari interleaved bitplanes (8 planes) support' CONFIG_FBCON_IPLAN2P8
- tristate '8 bpp packed pixel support' CONFIG_FBCON_CFB8
- tristate '16 bpp packed pixel support' CONFIG_FBCON_CFB16
- tristate 'Cybervision support (accelerated)' CONFIG_FBCON_CYBER
- tristate 'RetinaZ3 support (accelerated)' CONFIG_FBCON_RETINAZ3
+ bool 'Monochrome support' CONFIG_FBCON_MFB
+ bool '2 bpp packed pixels support' CONFIG_FBCON_CFB2
+ bool '4 bpp packed pixels support' CONFIG_FBCON_CFB4
+ bool '8 bpp packed pixels support' CONFIG_FBCON_CFB8
+ bool '16 bpp packed pixels support' CONFIG_FBCON_CFB16
+ bool '24 bpp packed pixels support' CONFIG_FBCON_CFB24
+ bool '32 bpp packed pixels support' CONFIG_FBCON_CFB32
+ bool 'Amiga bitplanes support' CONFIG_FBCON_AFB
+ bool 'Amiga interleaved bitplanes support' CONFIG_FBCON_ILBM
+ bool 'Atari interleaved bitplanes (2 planes) support' CONFIG_FBCON_IPLAN2P2
+ bool 'Atari interleaved bitplanes (4 planes) support' CONFIG_FBCON_IPLAN2P4
+ bool 'Atari interleaved bitplanes (8 planes) support' CONFIG_FBCON_IPLAN2P8
+ bool 'Mac variable bpp packed pixels support' CONFIG_FBCON_MAC
else
- if [ "$CONFIG_FB_AMIGA" != "n" -o "$CONFIG_FB_ATARI" != "n" -o \
- "$CONFIG_FB_CYBER" != "n" -o "$CONFIG_FB_RETINAZ3" != "n" -o \
- "$CONFIG_FB_VIRTUAL" != "n" ]; then
+ if [ "$CONFIG_FB_AMIGA" = "y" -o "$CONFIG_FB_AMIGA" = "m" -o \
+ "$CONFIG_FB_ATARI" = "y" -o "$CONFIG_FB_ATARI" = "m" -o \
+ "$CONFIG_FB_CYBER" = "y" -o "$CONFIG_FB_CYBER" = "m" -o \
+ "$CONFIG_FB_RETINAZ3" = "y" -o "$CONFIG_FB_RETINAZ3" = "m" -o \
+ "$CONFIG_FB_VIRGE" = "y" -o "$CONFIG_FB_VIRGE" = "m" -o \
+ "$CONFIG_FB_MAC" = "y" -o "$CONFIG_FB_MAC" = "m" -o \
+ "$CONFIG_FB_VIRTUAL" = "y" -o "$CONFIG_FB_VIRTUAL" = "m" ]; then
define_bool CONFIG_FBCON_MFB y
fi
if [ "$CONFIG_FB_AMIGA" = "y" -o "$CONFIG_FB_AMIGA" = "m" ]; then
@@ -55,20 +82,32 @@ if [ "$CONFIG_FB" = "y" ]; then
define_bool CONFIG_FBCON_IPLAN2P4 y
define_bool CONFIG_FBCON_IPLAN2P8 y
fi
+ if [ "$CONFIG_FB_MAC" = "y" -o "$CONFIG_FB_MAC" = "m" -o \
+ "$CONFIG_FB_VIRTUAL" = "y" -o "$CONFIG_FB_VIRTUAL" = "m" ]; then
+ define_bool CONFIG_FBCON_MAC y
+ define_bool CONFIG_FBCON_CFB2 y
+ define_bool CONFIG_FBCON_CFB4 y
+ fi
if [ "$CONFIG_FB_ATARI" = "y" -o "$CONFIG_FB_ATARI" = "m" -o \
- "$CONFIG_FB_OPEN_FIRMWARE" = "y" -o \
+ "$CONFIG_FB_OF" = "y" -o "$CONFIG_FB_OF" = "m" -o \
+ "$CONFIG_FB_MAC" = "y" -o "$CONFIG_FB_MAC" = "m" -o \
+ "$CONFIG_FB_TGA" = "y" -o "$CONFIG_FB_TGA" = "m" -o \
"$CONFIG_FB_VIRTUAL" = "y" -o "$CONFIG_FB_VIRTUAL" = "m" ]; then
define_bool CONFIG_FBCON_CFB8 y
fi
if [ "$CONFIG_FB_ATARI" = "y" -o "$CONFIG_FB_ATARI" = "m" -o \
+ "$CONFIG_FB_ATY" = "y" -o "$CONFIG_FB_ATY" = "m" -o \
+ "$CONFIG_FB_MAC" = "y" -o "$CONFIG_FB_MAC" = "m" -o \
"$CONFIG_FB_VIRTUAL" = "y" -o "$CONFIG_FB_VIRTUAL" = "m" ]; then
define_bool CONFIG_FBCON_CFB16 y
fi
- if [ "$CONFIG_FB_CYBER" = "y" -o "$CONFIG_FB_CYBER" = "m" ]; then
- define_bool CONFIG_FBCON_CYBER y
+ if [ "$CONFIG_FB_VIRTUAL" = "y" -o "$CONFIG_FB_VIRTUAL" = "m" ]; then
+ define_bool CONFIG_FBCON_CFB24 y
fi
- if [ "$CONFIG_FB_RETINAZ3" = "y" -o "$CONFIG_FB_RETINAZ3" = "m" ]; then
- define_bool CONFIG_FBCON_RETINAZ3 y
+ if [ "$CONFIG_FB_ATARI" = "y" -o "$CONFIG_FB_ATARI" = "m" -o \
+ "$CONFIG_FB_ATY" = "y" -o "$CONFIG_FB_ATY" = "m" -o \
+ "$CONFIG_FB_VIRTUAL" = "y" -o "$CONFIG_FB_VIRTUAL" = "m" ]; then
+ define_bool CONFIG_FBCON_CFB32 y
fi
fi
diff --git a/drivers/video/Makefile b/drivers/video/Makefile
index ebed69d68..2349e4720 100644
--- a/drivers/video/Makefile
+++ b/drivers/video/Makefile
@@ -22,15 +22,11 @@ MOD_LIST_NAME := VIDEO_MODULES
# Frame Buffer Console
ifeq ($(CONFIG_FB),y)
- L_OBJS += fonts.o font_8x8.o font_8x16.o pearl_8x8.o
- LX_OBJS += fbcon.o fbcmap.o
+ L_OBJS += fonts.o font_8x8.o font_8x16.o pearl_8x8.o font_6x11.o
+ LX_OBJS += fbcon.o fbcmap.o fbgen.o
endif
-# Frame buffer devices
-
-ifeq ($(CONFIG_APOLLO),y)
-L_OBJS += dn_fb.o
-endif
+# Frame Buffer Devices
ifeq ($(CONFIG_FB_AMIGA),y)
L_OBJS += amifb.o
@@ -40,6 +36,10 @@ else
endif
endif
+ifeq ($(CONFIG_FB_APOLLO),y)
+L_OBJS += dnfb.o
+endif
+
ifeq ($(CONFIG_FB_ATARI),y)
L_OBJS += atafb.o
else
@@ -48,134 +48,114 @@ else
endif
endif
+ifeq ($(CONFIG_FB_ATY),y)
+L_OBJS += atyfb.o
+endif
+
ifeq ($(CONFIG_FB_CYBER),y)
-LX_OBJS += cyberfb.o
+L_OBJS += cyberfb.o
else
ifeq ($(CONFIG_FB_CYBER),m)
- MX_OBJS += cyberfb.o
+ M_OBJS += cyberfb.o
endif
endif
+ifeq ($(CONFIG_FB_MAC),y)
+L_OBJS += macfb.o
+endif
+
+ifeq ($(CONFIG_FB_OF),y)
+L_OBJS += offb.o
+endif
+
ifeq ($(CONFIG_FB_RETINAZ3),y)
-LX_OBJS += retz3fb.o
+L_OBJS += retz3fb.o
else
ifeq ($(CONFIG_FB_RETINAZ3),m)
- MX_OBJS += retz3fb.o
+ M_OBJS += retz3fb.o
endif
endif
-ifeq ($(CONFIG_FB_VIRTUAL),y)
-L_OBJS += vfb.o
+ifeq ($(CONFIG_FB_S3TRIO),y)
+L_OBJS += S3triofb.o
else
- ifeq ($(CONFIG_FB_VIRTUAL),m)
- M_OBJS += vfb.o
+ ifeq ($(CONFIG_FB_S3TRIO),m)
+ M_OBJS += S3triofb.o
endif
endif
-ifeq ($(CONFIG_FB_OPEN_FIRMWARE),y)
-L_OBJS += offb.o
+ifeq ($(CONFIG_FB_TGA),y)
+L_OBJS += tgafb.o
endif
-ifeq ($(CONFIG_FB_MACH64),y)
-L_OBJS += mach64fb.o
+ifeq ($(CONFIG_FB_VIRGE),y)
+L_OBJS += virgefb.o
else
- ifeq ($(CONFIG_FB_MACH64),m)
- M_OBJS += mach64fb.o
+ ifeq ($(CONFIG_FB_VIRGE),m)
+ M_OBJS += virgefb.o
endif
endif
-ifeq ($(CONFIG_FB_TGA),y)
-L_OBJS += tgafb.o
+ifeq ($(CONFIG_FB_VIRTUAL),y)
+L_OBJS += vfb.o
+else
+ ifeq ($(CONFIG_FB_VIRTUAL),m)
+ M_OBJS += vfb.o
+ endif
endif
-# Low level drivers
+# Generic Low Level Drivers
-ifeq ($(CONFIG_FBCON_AFB),y)
-L_OBJS += fbcon-afb.o
-else
- ifeq ($(CONFIG_FBCON_AFB),m)
- M_OBJS += fbcon-afb.o
- endif
+ifdef CONFIG_FBCON_AFB
+LX_OBJS += fbcon-afb.o
endif
-ifeq ($(CONFIG_FBCON_CFB8),y)
-L_OBJS += fbcon-cfb8.o
-else
- ifeq ($(CONFIG_FBCON_CFB8),m)
- M_OBJS += fbcon-cfb8.o
- endif
+ifdef CONFIG_FBCON_CFB2
+LX_OBJS += fbcon-cfb2.o
endif
-ifeq ($(CONFIG_FBCON_CFB16),y)
+ifdef CONFIG_FBCON_CFB4
+LX_OBJS += fbcon-cfb4.o
+endif
+
+ifdef CONFIG_FBCON_CFB8
+LX_OBJS += fbcon-cfb8.o
+endif
+
+ifdef CONFIG_FBCON_CFB16
LX_OBJS += fbcon-cfb16.o
-else
- ifeq ($(CONFIG_FBCON_CFB16),m)
- MX_OBJS += fbcon-cfb16.o
- endif
endif
-ifeq ($(CONFIG_FBCON_ILBM),y)
-L_OBJS += fbcon-ilbm.o
-else
- ifeq ($(CONFIG_FBCON_ILBM),m)
- M_OBJS += fbcon-ilbm.o
- endif
+ifdef CONFIG_FBCON_CFB24
+LX_OBJS += fbcon-cfb24.o
endif
-ifeq ($(CONFIG_FBCON_IPLAN2P2),y)
-L_OBJS += fbcon-iplan2p2.o
-else
- ifeq ($(CONFIG_FBCON_IPLAN2P2),m)
- M_OBJS += fbcon-iplan2p2.o
- endif
+ifdef CONFIG_FBCON_CFB32
+LX_OBJS += fbcon-cfb32.o
endif
-ifeq ($(CONFIG_FBCON_IPLAN2P4),y)
-L_OBJS += fbcon-iplan2p4.o
-else
- ifeq ($(CONFIG_FBCON_IPLAN2P4),m)
- M_OBJS += fbcon-iplan2p4.o
- endif
+ifdef CONFIG_FBCON_ILBM
+LX_OBJS += fbcon-ilbm.o
endif
-ifeq ($(CONFIG_FBCON_IPLAN2P8),y)
-L_OBJS += fbcon-iplan2p8.o
-else
- ifeq ($(CONFIG_FBCON_IPLAN2P8),m)
- M_OBJS += fbcon-iplan2p8.o
- endif
+ifdef CONFIG_FBCON_IPLAN2P2
+LX_OBJS += fbcon-iplan2p2.o
endif
-ifeq ($(CONFIG_FBCON_MFB),y)
-L_OBJS += fbcon-mfb.o
-else
- ifeq ($(CONFIG_FBCON_MFB),m)
- M_OBJS += fbcon-mfb.o
- endif
+ifdef CONFIG_FBCON_IPLAN2P4
+LX_OBJS += fbcon-iplan2p4.o
endif
-ifeq ($(CONFIG_FBCON_CYBER),y)
-L_OBJS += fbcon-cyber.o
-else
- ifeq ($(CONFIG_FBCON_CYBER),m)
- M_OBJS += fbcon-cyber.o
- endif
+ifdef CONFIG_FBCON_IPLAN2P8
+LX_OBJS += fbcon-iplan2p8.o
endif
-ifeq ($(CONFIG_FBCON_RETINAZ3),y)
-L_OBJS += fbcon-retz3.o
-else
- ifeq ($(CONFIG_FBCON_RETINAZ3),m)
- M_OBJS += fbcon-retz3.o
- endif
+ifdef CONFIG_FBCON_MAC
+LX_OBJS += fbcon-mac.o
endif
-ifeq ($(CONFIG_FBCON_MACH64),y)
-L_OBJS += fbcon-mach64.o
-else
- ifeq ($(CONFIG_FBCON_MACH64),m)
- M_OBJS += fbcon-mach64.o
- endif
+ifdef CONFIG_FBCON_MFB
+LX_OBJS += fbcon-mfb.o
endif
# GSP Console
@@ -184,7 +164,7 @@ ifdef CONFIG_AMIGA_GSP
L_OBJS := $(L_OBJS) gspcon.o gspcore.o
endif
-# VGA Console
+# VGA Text Console
ifdef CONFIG_ABSTRACT_CONSOLE
ifdef CONFIG_VGA_CONSOLE
diff --git a/drivers/video/S3triofb.c b/drivers/video/S3triofb.c
new file mode 100644
index 000000000..16c0b888a
--- /dev/null
+++ b/drivers/video/S3triofb.c
@@ -0,0 +1,885 @@
+/*
+ * linux/drivers/video/S3Triofb.c -- Open Firmware based frame buffer device
+ *
+ * Copyright (C) 1997 Peter De Schrijver
+ *
+ * This driver is partly based on the PowerMac console driver:
+ *
+ * Copyright (C) 1996 Paul Mackerras
+ *
+ * and on the Open Firmware based frame buffer device:
+ *
+ * Copyright (C) 1997 Geert Uytterhoeven
+ *
+ * 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.
+ */
+
+/*
+ Bugs : + OF dependencies should be removed.
+ + This driver should be merged with the CyberVision driver. The
+ CyberVision is a Zorro III implementation of the S3Trio64 chip.
+
+*/
+
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/mm.h>
+#include <linux/tty.h>
+#include <linux/malloc.h>
+#include <linux/vmalloc.h>
+#include <linux/delay.h>
+#include <linux/interrupt.h>
+#include <linux/fb.h>
+#include <linux/init.h>
+#include <asm/io.h>
+#include <asm/prom.h>
+#include <linux/pci.h>
+
+#include "fbcon-cfb8.h"
+
+
+#define mem_in8(addr) in_8((void *)(addr))
+#define mem_in16(addr) in_le16((void *)(addr))
+#define mem_in32(addr) in_le32((void *)(addr))
+
+#define mem_out8(val, addr) out_8((void *)(addr), val)
+#define mem_out16(val, addr) out_le16((void *)(addr), val)
+#define mem_out32(val, addr) out_le32((void *)(addr), val)
+
+#define IO_OUT16VAL(v, r) (((v) << 8) | (r))
+
+#define arraysize(x) (sizeof(x)/sizeof(*(x)))
+
+static int currcon = 0;
+static struct display disp;
+static struct fb_info fb_info;
+static struct { u_char red, green, blue, pad; } palette[256];
+static char s3trio_name[16] = "S3Trio ";
+
+
+static struct fb_fix_screeninfo fb_fix;
+static struct fb_var_screeninfo fb_var = { 0, };
+
+
+ /*
+ * Interface used by the world
+ */
+
+void of_video_setup(char *options, int *ints);
+
+static int s3trio_open(struct fb_info *info);
+static int s3trio_release(struct fb_info *info);
+static int s3trio_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int s3trio_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int s3trio_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int s3trio_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int s3trio_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int s3trio_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int s3trio_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info);
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+extern struct vc_mode display_info;
+extern struct fb_info *console_fb_info;
+extern int (*console_setmode_ptr)(struct vc_mode *, int);
+extern int (*console_set_cmap_ptr)(struct fb_cmap *, int, int,
+ struct fb_info *);
+static int s3trio_console_setmode(struct vc_mode *mode, int doit);
+#endif /* CONFIG_FB_COMPAT_XPMAC */
+
+ /*
+ * Interface to the low level console driver
+ */
+
+unsigned long s3trio_fb_init(unsigned long mem_start);
+static int s3triofbcon_switch(int con, struct fb_info *info);
+static int s3triofbcon_updatevar(int con, struct fb_info *info);
+static void s3triofbcon_blank(int blank, struct fb_info *info);
+static int s3triofbcon_setcmap(struct fb_cmap *cmap, int con);
+
+ /*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static struct display_switch fbcon_trio8;
+#endif
+
+ /*
+ * Accelerated Functions used by the low level console driver
+ */
+
+static void Trio_WaitQueue(u_short fifo);
+static void Trio_WaitBlit(void);
+static void Trio_BitBLT(u_short curx, u_short cury, u_short destx,
+ u_short desty, u_short width, u_short height,
+ u_short mode);
+static void Trio_RectFill(u_short x, u_short y, u_short width, u_short height,
+ u_short mode, u_short color);
+static void Trio_MoveCursor(u_short x, u_short y);
+
+
+ /*
+ * Internal routines
+ */
+
+static int s3trio_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info);
+static int s3trio_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info);
+static void do_install_cmap(int con);
+
+
+static struct fb_ops s3trio_ops = {
+ s3trio_open, s3trio_release, s3trio_get_fix, s3trio_get_var, s3trio_set_var,
+ s3trio_get_cmap, s3trio_set_cmap, s3trio_pan_display, NULL, s3trio_ioctl
+};
+
+
+ /*
+ * Open/Release the frame buffer device
+ */
+
+static int s3trio_open(struct fb_info *info)
+{
+ /*
+ * Nothing, only a usage count for the moment
+ */
+
+ MOD_INC_USE_COUNT;
+ return(0);
+}
+
+static int s3trio_release(struct fb_info *info)
+{
+ MOD_DEC_USE_COUNT;
+ return(0);
+}
+
+
+ /*
+ * Get the Fixed Part of the Display
+ */
+
+static int s3trio_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
+{
+ memcpy(fix, &fb_fix, sizeof(fb_fix));
+ return 0;
+}
+
+
+ /*
+ * Get the User Defined Part of the Display
+ */
+
+static int s3trio_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ memcpy(var, &fb_var, sizeof(fb_var));
+ return 0;
+}
+
+
+ /*
+ * Set the User Defined Part of the Display
+ */
+
+static int s3trio_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ if (var->xres > fb_var.xres || var->yres > fb_var.yres ||
+ var->xres_virtual > fb_var.xres_virtual ||
+ var->yres_virtual > fb_var.yres_virtual ||
+ var->bits_per_pixel > fb_var.bits_per_pixel ||
+ var->nonstd || var->vmode != FB_VMODE_NONINTERLACED)
+ return -EINVAL;
+ memcpy(var, &fb_var, sizeof(fb_var));
+ return 0;
+}
+
+
+ /*
+ * Pan or Wrap the Display
+ *
+ * This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
+ */
+
+static int s3trio_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ if (var->xoffset || var->yoffset)
+ return -EINVAL;
+ else
+ return 0;
+}
+
+ /*
+ * Get the Colormap
+ */
+
+static int s3trio_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ if (con == currcon) /* current console? */
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, s3trio_getcolreg,
+ info);
+ else if (fb_display[con].cmap.len) /* non default colormap? */
+ fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
+ else
+ fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ cmap, kspc ? 0 : 2);
+ return 0;
+}
+
+ /*
+ * Set the Colormap
+ */
+
+static int s3trio_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ int err;
+
+
+ if (!fb_display[con].cmap.len) { /* no colormap allocated? */
+ if ((err = fb_alloc_cmap(&fb_display[con].cmap,
+ 1<<fb_display[con].var.bits_per_pixel, 0)))
+ return err;
+ }
+ if (con == currcon) /* current console? */
+ return fb_set_cmap(cmap, &fb_display[con].var, kspc, s3trio_setcolreg,
+ info);
+ else
+ fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
+ return 0;
+}
+
+
+static int s3trio_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info)
+{
+ return -EINVAL;
+}
+
+__initfunc(int s3trio_resetaccel(void)) {
+
+
+#define EC01_ENH_ENB 0x0005
+#define EC01_LAW_ENB 0x0010
+#define EC01_MMIO_ENB 0x0020
+
+#define EC00_RESET 0x8000
+#define EC00_ENABLE 0x4000
+#define MF_MULT_MISC 0xE000
+#define SRC_FOREGROUND 0x0020
+#define SRC_BACKGROUND 0x0000
+#define MIX_SRC 0x0007
+#define MF_T_CLIP 0x1000
+#define MF_L_CLIP 0x2000
+#define MF_B_CLIP 0x3000
+#define MF_R_CLIP 0x4000
+#define MF_PIX_CONTROL 0xA000
+#define MFA_SRC_FOREGR_MIX 0x0000
+#define MF_PIX_CONTROL 0xA000
+
+ outw(EC00_RESET, 0x42e8);
+ inw( 0x42e8);
+ outw(EC00_ENABLE, 0x42e8);
+ inw( 0x42e8);
+ outw(EC01_ENH_ENB | EC01_LAW_ENB,
+ 0x4ae8);
+ outw(MF_MULT_MISC, 0xbee8); /* 16 bit I/O registers */
+
+ /* Now set some basic accelerator registers */
+ Trio_WaitQueue(0x0400);
+ outw(SRC_FOREGROUND | MIX_SRC, 0xbae8);
+ outw(SRC_BACKGROUND | MIX_SRC, 0xb6e8);/* direct color*/
+ outw(MF_T_CLIP | 0, 0xbee8 ); /* clip virtual area */
+ outw(MF_L_CLIP | 0, 0xbee8 );
+ outw(MF_R_CLIP | (640 - 1), 0xbee8);
+ outw(MF_B_CLIP | (480 - 1), 0xbee8);
+ Trio_WaitQueue(0x0400);
+ outw(0xffff, 0xaae8); /* Enable all planes */
+ outw(0xffff, 0xaae8); /* Enable all planes */
+ outw( MF_PIX_CONTROL | MFA_SRC_FOREGR_MIX, 0xbee8);
+
+}
+
+__initfunc(int s3trio_init(void)) {
+
+ u_char bus, dev;
+ unsigned int t32;
+ unsigned short cmd;
+ int i;
+
+ bus=0;
+ dev=(3<<3);
+ pcibios_read_config_dword(bus, dev, PCI_VENDOR_ID, &t32);
+ if(t32 == (PCI_DEVICE_ID_S3_TRIO << 16) + PCI_VENDOR_ID_S3) {
+ pcibios_read_config_dword(bus, dev, PCI_BASE_ADDRESS_0, &t32);
+ pcibios_read_config_dword(bus, dev, PCI_BASE_ADDRESS_1, &t32);
+ pcibios_read_config_word(bus, dev, PCI_COMMAND,&cmd);
+
+ pcibios_write_config_word(bus, dev, PCI_COMMAND, PCI_COMMAND_IO | PCI_COMMAND_MEMORY);
+
+ pcibios_write_config_dword(bus, dev, PCI_BASE_ADDRESS_0,0xffffffff);
+ pcibios_read_config_dword(bus, dev, PCI_BASE_ADDRESS_0, &t32);
+
+/* This is a gross hack as OF only maps enough memory for the framebuffer and
+ we want to use MMIO too. We should find out which chunk of address space
+ we can use here */
+ pcibios_write_config_dword(bus,dev,PCI_BASE_ADDRESS_0,0xc6000000);
+
+ /* unlock s3 */
+
+ outb(0x01, 0x3C3);
+
+ outb(inb(0x03CC) | 1, 0x3c2);
+
+ outw(IO_OUT16VAL(0x48, 0x38),0x03D4);
+ outw(IO_OUT16VAL(0xA0, 0x39),0x03D4);
+ outb(0x33,0x3d4);
+ outw(IO_OUT16VAL( inb(0x3d5) & ~(0x2 |
+ 0x10 | 0x40) , 0x33),0x3d4);
+
+ outw(IO_OUT16VAL(0x6,0x8), 0x3c4);
+
+ /* switch to MMIO only mode */
+
+ outb(0x58,0x3d4);
+ outw(IO_OUT16VAL(inb(0x3d5) | 3 | 0x10,0x58),0x3d4);
+ outw(IO_OUT16VAL(8,0x53),0x3d4);
+
+ /* switch off I/O accesses */
+
+#if 0
+ pcibios_write_config_word(bus, dev, PCI_COMMAND,
+ PCI_COMMAND_IO | PCI_COMMAND_MEMORY);
+#endif
+ }
+
+ return 0;
+}
+
+
+ /*
+ * Initialisation
+ * We heavily rely on OF for the moment. This needs fixing.
+ */
+
+__initfunc(unsigned long s3trio_fb_init(unsigned long mem_start))
+{
+ struct device_node *dp;
+ int i, err, *pp, len;
+ unsigned *up, address;
+ u_long *CursorBase;
+
+ if (!prom_display_paths[0])
+ return mem_start;
+ if (!(dp = find_path_device(prom_display_paths[0])))
+ return mem_start;
+
+ strncat(s3trio_name, dp->name, sizeof(s3trio_name));
+ s3trio_name[sizeof(s3trio_name)-1] = '\0';
+ strcpy(fb_fix.id, s3trio_name);
+
+ if((pp = (int *)get_property(dp, "vendor-id", &len)) != NULL
+ && *pp!=PCI_VENDOR_ID_S3) {
+ printk("%s: can't find S3 Trio board\n", dp->full_name);
+ return mem_start;
+ }
+
+ if((pp = (int *)get_property(dp, "device-id", &len)) != NULL
+ && *pp!=PCI_DEVICE_ID_S3_TRIO) {
+ printk("%s: can't find S3 Trio board\n", dp->full_name);
+ return mem_start;
+ }
+
+ if ((pp = (int *)get_property(dp, "depth", &len)) != NULL
+ && len == sizeof(int) && *pp != 8) {
+ printk("%s: can't use depth = %d\n", dp->full_name, *pp);
+ return mem_start;
+ }
+ if ((pp = (int *)get_property(dp, "width", &len)) != NULL
+ && len == sizeof(int))
+ fb_var.xres = fb_var.xres_virtual = *pp;
+ if ((pp = (int *)get_property(dp, "height", &len)) != NULL
+ && len == sizeof(int))
+ fb_var.yres = fb_var.yres_virtual = *pp;
+ if ((pp = (int *)get_property(dp, "linebytes", &len)) != NULL
+ && len == sizeof(int))
+ fb_fix.line_length = *pp;
+ else
+ fb_fix.line_length = fb_var.xres_virtual;
+ fb_fix.smem_len = fb_fix.line_length*fb_var.yres;
+
+ s3trio_init();
+ address=0xc6000000;
+ fb_fix.smem_start = ioremap(address,64*1024*1024);
+ fb_fix.type = FB_TYPE_PACKED_PIXELS;
+ fb_fix.type_aux = 0;
+
+
+ s3trio_resetaccel();
+
+ mem_out8(0x30,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0x2d,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0x2e,fb_fix.smem_start+0x1008000 + 0x03D4);
+
+ mem_out8(0x50,fb_fix.smem_start+0x1008000 + 0x03D4);
+
+ /* disable HW cursor */
+
+ mem_out8(0x39,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0xa0,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x45,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x4e,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x4f,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ /* init HW cursor */
+
+ CursorBase=(u_long *)(fb_fix.smem_start + 2*1024*1024 - 0x400);
+ for (i=0; i < 8; i++) {
+ *(CursorBase +(i*4)) = 0xffffff00;
+ *(CursorBase+1+(i*4)) = 0xffff0000;
+ *(CursorBase+2+(i*4)) = 0xffff0000;
+ *(CursorBase+3+(i*4)) = 0xffff0000;
+ }
+ for (i=8; i < 64; i++) {
+ *(CursorBase +(i*4)) = 0xffff0000;
+ *(CursorBase+1+(i*4)) = 0xffff0000;
+ *(CursorBase+2+(i*4)) = 0xffff0000;
+ *(CursorBase+3+(i*4)) = 0xffff0000;
+ }
+
+
+ mem_out8(0x4c,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(((2*1024 - 1)&0xf00)>>8,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x4d,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8((2*1024 - 1) & 0xff,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x45,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_in8(fb_fix.smem_start+0x1008000 + 0x03D4);
+
+ mem_out8(0x4a,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0x80,fb_fix.smem_start+0x1008000 + 0x03D5);
+ mem_out8(0x80,fb_fix.smem_start+0x1008000 + 0x03D5);
+ mem_out8(0x80,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x4b,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0x00,fb_fix.smem_start+0x1008000 + 0x03D5);
+ mem_out8(0x00,fb_fix.smem_start+0x1008000 + 0x03D5);
+ mem_out8(0x00,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ mem_out8(0x45,fb_fix.smem_start+0x1008000 + 0x03D4);
+ mem_out8(0,fb_fix.smem_start+0x1008000 + 0x03D5);
+
+ s3trio_setcolreg(255, 56, 100, 160, 0, NULL /* not used */);
+ s3trio_setcolreg(254, 0, 0, 0, 0, NULL /* not used */);
+ memset((char *)fb_fix.smem_start,0,640*480);
+
+#if 0
+ Trio_RectFill(0,0,90,90,7,1);
+#endif
+
+ fb_fix.visual = FB_VISUAL_PSEUDOCOLOR ;
+ fb_var.xoffset = fb_var.yoffset = 0;
+ fb_var.bits_per_pixel = 8;
+ fb_var.grayscale = 0;
+ fb_var.red.offset = fb_var.green.offset = fb_var.blue.offset = 0;
+ fb_var.red.length = fb_var.green.length = fb_var.blue.length = 8;
+ fb_var.red.msb_right = fb_var.green.msb_right = fb_var.blue.msb_right = 0;
+ fb_var.transp.offset = fb_var.transp.length = fb_var.transp.msb_right = 0;
+ fb_var.nonstd = 0;
+ fb_var.activate = 0;
+ fb_var.height = fb_var.width = -1;
+ fb_var.accel = 5;
+ fb_var.pixclock = 1;
+ fb_var.left_margin = fb_var.right_margin = 0;
+ fb_var.upper_margin = fb_var.lower_margin = 0;
+ fb_var.hsync_len = fb_var.vsync_len = 0;
+ fb_var.sync = 0;
+ fb_var.vmode = FB_VMODE_NONINTERLACED;
+
+ disp.var = fb_var;
+ disp.cmap.start = 0;
+ disp.cmap.len = 0;
+ disp.cmap.red = disp.cmap.green = disp.cmap.blue = disp.cmap.transp = NULL;
+ disp.screen_base = fb_fix.smem_start;
+ disp.visual = fb_fix.visual;
+ disp.type = fb_fix.type;
+ disp.type_aux = fb_fix.type_aux;
+ disp.ypanstep = 0;
+ disp.ywrapstep = 0;
+ disp.line_length = fb_fix.line_length;
+ disp.can_soft_blank = 1;
+ disp.inverse = 0;
+#ifdef CONFIG_FBCON_CFB8
+ disp.dispsw = &fbcon_trio8;
+#else
+ disp.dispsw = NULL;
+#endif
+
+ strcpy(fb_info.modename, "Trio64 ");
+ strncat(fb_info.modename, dp->full_name, sizeof(fb_info.modename));
+ fb_info.node = -1;
+ fb_info.fbops = &s3trio_ops;
+#if 0
+ fb_info.fbvar_num = 1;
+ fb_info.fbvar = &fb_var;
+#endif
+ fb_info.disp = &disp;
+ fb_info.fontname[0] = '\0';
+ fb_info.changevar = NULL;
+ fb_info.switch_con = &s3triofbcon_switch;
+ fb_info.updatevar = &s3triofbcon_updatevar;
+ fb_info.blank = &s3triofbcon_blank;
+#if 0
+ fb_info.setcmap = &s3triofbcon_setcmap;
+#endif
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+ if (!console_fb_info) {
+ display_info.height = fb_var.yres;
+ display_info.width = fb_var.xres;
+ display_info.depth = 8;
+ display_info.pitch = fb_fix.line_length;
+ display_info.mode = 0;
+ strncpy(display_info.name, dp->name, sizeof(display_info.name));
+ display_info.fb_address = (unsigned long)fb_fix.smem_start;
+ display_info.disp_reg_address = address + 0x1008000;
+ display_info.cmap_adr_address = address + 0x1008000 + 0x3c8;
+ display_info.cmap_data_address = address + 0x1008000 + 0x3c9;
+ console_fb_info = &fb_info;
+ console_setmode_ptr = s3trio_console_setmode;
+ console_set_cmap_ptr = s3trio_set_cmap;
+ }
+#endif /* CONFIG_FB_COMPAT_XPMAC) */
+
+ err = register_framebuffer(&fb_info);
+ if (err < 0)
+ return mem_start;
+
+ printk("fb%d: S3 Trio frame buffer device on %s\n",
+ GET_FB_IDX(fb_info.node), dp->full_name);
+
+ return mem_start;
+}
+
+
+static int s3triofbcon_switch(int con, struct fb_info *info)
+{
+ /* Do we have to save the colormap? */
+ if (fb_display[currcon].cmap.len)
+ fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
+ s3trio_getcolreg, info);
+
+ currcon = con;
+ /* Install new colormap */
+ do_install_cmap(con);
+ return 0;
+}
+
+ /*
+ * Update the `var' structure (called by fbcon.c)
+ */
+
+static int s3triofbcon_updatevar(int con, struct fb_info *info)
+{
+ /* Nothing */
+ return 0;
+}
+
+ /*
+ * Blank the display.
+ */
+
+static void s3triofbcon_blank(int blank, struct fb_info *info)
+{
+ /* Nothing */
+}
+
+ /*
+ * Set the colormap
+ */
+
+static int s3triofbcon_setcmap(struct fb_cmap *cmap, int con)
+{
+ return(s3trio_set_cmap(cmap, 1, con, &fb_info));
+}
+
+
+ /*
+ * Read a single color register and split it into
+ * colors/transparent. Return != 0 for invalid regno.
+ */
+
+static int s3trio_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info)
+{
+ if (regno > 255)
+ return 1;
+ *red = palette[regno].red;
+ *green = palette[regno].green;
+ *blue = palette[regno].blue;
+ return 0;
+}
+
+
+ /*
+ * Set a single color register. The values supplied are already
+ * rounded down to the hardware's capabilities (according to the
+ * entries in the var structure). Return != 0 for invalid regno.
+ */
+
+static int s3trio_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info)
+{
+ if (regno > 255)
+ return 1;
+ palette[regno].red = red;
+ palette[regno].green = green;
+ palette[regno].blue = blue;
+
+ mem_out8(regno,fb_fix.smem_start+0x1008000 + 0x3c8);
+ mem_out8((red & 0xff) >> 2,fb_fix.smem_start+0x1008000 + 0x3c9);
+ mem_out8((green & 0xff) >> 2,fb_fix.smem_start+0x1008000 + 0x3c9);
+ mem_out8((blue & 0xff) >> 2,fb_fix.smem_start+0x1008000 + 0x3c9);
+
+ return 0;
+}
+
+
+static void do_install_cmap(int con)
+{
+ if (con != currcon)
+ return;
+ if (fb_display[con].cmap.len)
+ fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
+ s3trio_setcolreg, &fb_info);
+ else
+ fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, s3trio_setcolreg, &fb_info);
+}
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+
+ /*
+ * Backward compatibility mode for Xpmac
+ */
+
+static int s3trio_console_setmode(struct vc_mode *mode, int doit)
+{
+ int err;
+ struct fb_var_screeninfo var;
+ struct s3trio_par par;
+
+ if (mode->mode <= 0 || mode->mode > VMODE_MAX )
+ return -EINVAL;
+ par.video_mode = mode->mode;
+
+ switch (mode->depth) {
+ case 24:
+ case 32:
+ par.color_mode = CMODE_32;
+ break;
+ case 16:
+ par.color_mode = CMODE_16;
+ break;
+ case 8:
+ case 0: /* (default) */
+ par.color_mode = CMODE_8;
+ break;
+ default:
+ return -EINVAL;
+ }
+ encode_var(&var, &par);
+ if ((err = decode_var(&var, &par)))
+ return err;
+ if (doit)
+ s3trio_set_var(&var, currcon, 0);
+ return 0;
+}
+
+#endif /* CONFIG_FB_COMPAT_XPMAC */
+
+void s3trio_video_setup(char *options, int *ints) {
+
+ return;
+
+}
+
+static void Trio_WaitQueue(u_short fifo) {
+
+ u_short status;
+
+ do
+ {
+ status = mem_in16(fb_fix.smem_start + 0x1000000 + 0x9AE8);
+ } while (!(status & fifo));
+
+}
+
+static void Trio_WaitBlit(void) {
+
+ u_short status;
+
+ do
+ {
+ status = mem_in16(fb_fix.smem_start + 0x1000000 + 0x9AE8);
+ } while (status & 0x200);
+
+}
+
+static void Trio_BitBLT(u_short curx, u_short cury, u_short destx,
+ u_short desty, u_short width, u_short height,
+ u_short mode) {
+
+ u_short blitcmd = 0xc011;
+
+ /* Set drawing direction */
+ /* -Y, X maj, -X (default) */
+
+ if (curx > destx)
+ blitcmd |= 0x0020; /* Drawing direction +X */
+ else {
+ curx += (width - 1);
+ destx += (width - 1);
+ }
+
+ if (cury > desty)
+ blitcmd |= 0x0080; /* Drawing direction +Y */
+ else {
+ cury += (height - 1);
+ desty += (height - 1);
+ }
+
+ Trio_WaitQueue(0x0400);
+
+ outw(0xa000, 0xBEE8);
+ outw(0x60 | mode, 0xBAE8);
+
+ outw(curx, 0x86E8);
+ outw(cury, 0x82E8);
+
+ outw(destx, 0x8EE8);
+ outw(desty, 0x8AE8);
+
+ outw(height - 1, 0xBEE8);
+ outw(width - 1, 0x96E8);
+
+ outw(blitcmd, 0x9AE8);
+
+}
+
+static void Trio_RectFill(u_short x, u_short y, u_short width, u_short height,
+ u_short mode, u_short color) {
+
+ u_short blitcmd = 0x40b1;
+
+ Trio_WaitQueue(0x0400);
+
+ outw(0xa000, 0xBEE8);
+ outw((0x20 | mode), 0xBAE8);
+ outw(0xe000, 0xBEE8);
+ outw(color, 0xA6E8);
+ outw(x, 0x86E8);
+ outw(y, 0x82E8);
+ outw((height - 1), 0xBEE8);
+ outw((width - 1), 0x96E8);
+ outw(blitcmd, 0x9AE8);
+
+}
+
+
+static void Trio_MoveCursor(u_short x, u_short y) {
+
+ mem_out8(0x39, fb_fix.smem_start + 0x1008000 + 0x3d4);
+ mem_out8(0xa0, fb_fix.smem_start + 0x1008000 + 0x3d5);
+
+ mem_out8(0x46, fb_fix.smem_start + 0x1008000 + 0x3d4);
+ mem_out8((x & 0x0700) >> 8, fb_fix.smem_start + 0x1008000 + 0x3d5);
+ mem_out8(0x47, fb_fix.smem_start + 0x1008000 + 0x3d4);
+ mem_out8(x & 0x00ff, fb_fix.smem_start + 0x1008000 + 0x3d5);
+
+ mem_out8(0x48, fb_fix.smem_start + 0x1008000 + 0x3d4);
+ mem_out8((y & 0x0700) >> 8, fb_fix.smem_start + 0x1008000 + 0x3d5);
+ mem_out8(0x49, fb_fix.smem_start + 0x1008000 + 0x3d4);
+ mem_out8(y & 0x00ff, fb_fix.smem_start + 0x1008000 + 0x3d5);
+
+}
+
+
+ /*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static void fbcon_trio8_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width)
+{
+ sx *= 8; dx *= 8; width *= 8;
+ Trio_BitBLT((u_short)sx, (u_short)(sy*p->fontheight), (u_short)dx,
+ (u_short)(dy*p->fontheight), (u_short)width,
+ (u_short)(height*p->fontheight), (u_short)S3_NEW);
+}
+
+static void fbcon_trio8_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
+{
+ unsigned char bg;
+
+ sx *= 8; width *= 8;
+ bg = attr_bgcol_ec(p,conp);
+ Trio_RectFill((u_short)sx,
+ (u_short)(sy*p->fontheight),
+ (u_short)width,
+ (u_short)(height*p->fontheight),
+ (u_short)S3_NEW,
+ (u_short)bg);
+}
+
+static void fbcon_trio8_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx)
+{
+ Trio_WaitBlit();
+ fbcon_cfb8_putc(conp, p, c, yy, xx);
+}
+
+static void fbcon_trio8_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx)
+{
+ Trio_WaitBlit();
+ fbcon_cfb8_putcs(conp, p, s, count, yy, xx);
+}
+
+static void fbcon_trio8_revc(struct display *p, int xx, int yy)
+{
+ Trio_WaitBlit();
+ fbcon_cfb8_revc(p, xx, yy);
+}
+
+static struct display_switch fbcon_trio8 = {
+ fbcon_cfb8_setup, fbcon_trio8_bmove, fbcon_trio8_clear, fbcon_trio8_putc,
+ fbcon_trio8_putcs, fbcon_trio8_revc
+};
+#endif
diff --git a/drivers/video/amifb.c b/drivers/video/amifb.c
index 7aa9df61a..09ff067df 100644
--- a/drivers/video/amifb.c
+++ b/drivers/video/amifb.c
@@ -60,6 +60,11 @@
#include <asm/amigaints.h>
#include <asm/setup.h>
+#include "fbcon-afb.h"
+#include "fbcon-ilbm.h"
+#include "fbcon-mfb.h"
+
+
#define DEBUG
#if !defined(CONFIG_FB_AMIGA_OCS) && !defined(CONFIG_FB_AMIGA_ECS) && !defined(CONFIG_FB_AMIGA_AGA)
@@ -535,15 +540,6 @@ static u_short maxfmode, chipset;
/*
- * Monitor Specifications
- *
- * These are typical for a `generic' Amiga monitor (e.g. A1960)
- */
-
-static long vfmin = 50, vfmax = 90, hfmin = 15000, hfmax = 38000;
-
-
- /*
* Various macros
*/
@@ -672,7 +668,7 @@ static u_short *lofsprite, *shfsprite, *dummysprite;
* Current Video Mode
*/
-static struct amiga_fb_par {
+static struct amifb_par {
/* General Values */
@@ -740,6 +736,7 @@ static struct amiga_fb_par {
static int currcon = 0;
static struct display disp;
+
static struct fb_info fb_info;
@@ -789,229 +786,199 @@ static u_short is_lace = 0; /* Screen is laced */
* The rest of the name is filled in during initialization
*/
-static char amiga_fb_name[16] = "Amiga ";
+static char amifb_name[16] = "Amiga ";
- /*
- * Predefined Video Mode Names
- *
- * The a2024-?? modes don't work yet because there's no A2024 driver.
- */
-
-static char *amiga_fb_modenames[] = {
-
- /*
- * Autodetect (Default) Video Mode
- */
-
- "default",
/*
- * AmigaOS Video Modes
- */
-
- "ntsc", /* 640x200, 15 kHz, 60 Hz (NTSC) */
- "ntsc-lace", /* 640x400, 15 kHz, 60 Hz interlaced (NTSC) */
- "pal", /* 640x256, 15 kHz, 50 Hz (PAL) */
- "pal-lace", /* 640x512, 15 kHz, 50 Hz interlaced (PAL) */
- "multiscan", /* 640x480, 29 kHz, 57 Hz */
- "multiscan-lace", /* 640x960, 29 kHz, 57 Hz interlaced */
- "a2024-10", /* 1024x800, 10 Hz (Not yet supported) */
- "a2024-15", /* 1024x800, 15 Hz (Not yet supported) */
- "euro36", /* 640x200, 15 kHz, 72 Hz */
- "euro36-lace", /* 640x400, 15 kHz, 72 Hz interlaced */
- "euro72", /* 640x400, 29 kHz, 68 Hz */
- "euro72-lace", /* 640x800, 29 kHz, 68 Hz interlaced */
- "super72", /* 800x300, 23 kHz, 70 Hz */
- "super72-lace", /* 800x600, 23 kHz, 70 Hz interlaced */
- "dblntsc", /* 640x200, 27 kHz, 57 Hz doublescan */
- "dblntsc-ff", /* 640x400, 27 kHz, 57 Hz */
- "dblntsc-lace", /* 640x800, 27 kHz, 57 Hz interlaced */
- "dblpal", /* 640x256, 27 kHz, 47 Hz doublescan */
- "dblpal-ff", /* 640x512, 27 kHz, 47 Hz */
- "dblpal-lace", /* 640x1024, 27 kHz, 47 Hz interlaced */
-
- /*
- * VGA Video Modes
- */
-
- "vga", /* 640x480, 31 kHz, 60 Hz (VGA) */
- "vga70", /* 640x400, 31 kHz, 70 Hz (VGA) */
-
- /*
- * User Defined Video Modes: to be set after boot up using e.g. fbset
- */
-
- "user0", "user1", "user2", "user3", "user4", "user5", "user6", "user7"
-};
-
-static struct fb_var_screeninfo amiga_fb_predefined[] = {
-
- /*
- * Autodetect (Default) Video Mode
+ * Predefined Video Modes
+ *
*/
- { 0, },
-
- /*
- * AmigaOS Video Modes
- */
+static struct fb_videomode amifb_predefined[] __initdata = {
- {
- /* ntsc */
- 640, 200, 640, 200, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 106, 86, 44, 16, 76, 2,
- FB_SYNC_BROADCAST, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* ntsc-lace */
- 640, 400, 640, 400, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 106, 86, 88, 33, 76, 4,
- FB_SYNC_BROADCAST, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* pal */
- 640, 256, 640, 256, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 106, 86, 40, 14, 76, 2,
- FB_SYNC_BROADCAST, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* pal-lace */
- 640, 512, 640, 512, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 106, 86, 80, 29, 76, 4,
- FB_SYNC_BROADCAST, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* multiscan */
- 640, 480, 640, 480, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 96, 112, 29, 8, 72, 8,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
-
- }, {
- /* multiscan-lace */
- 640, 960, 640, 960, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 96, 112, 58, 16, 72, 16,
- 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* a2024-10 (Not yet supported) */
- 1024, 800, 1024, 800, 0, 0, 2, 0,
- {0, 2, 0}, {0, 2, 0}, {0, 2, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 0, 0, 0, 0, 0, 0,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* a2024-15 (Not yet supported) */
- 1024, 800, 1024, 800, 0, 0, 2, 0,
- {0, 2, 0}, {0, 2, 0}, {0, 2, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 0, 0, 0, 0, 0, 0,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* euro36 */
- 640, 200, 640, 200, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 92, 124, 6, 6, 52, 5,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* euro36-lace */
- 640, 400, 640, 400, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_HIRES, 92, 124, 12, 12, 52, 10,
- 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* euro72 */
- 640, 400, 640, 400, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 164, 92, 9, 9, 80, 8,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* euro72-lace */
- 640, 800, 640, 800, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 164, 92, 18, 18, 80, 16,
- 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* super72 */
- 800, 300, 800, 300, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 212, 140, 10, 11, 80, 7,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* super72-lace */
- 800, 600, 800, 600, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 212, 140, 20, 22, 80, 14,
- 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* dblntsc */
- 640, 200, 640, 200, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 196, 124, 18, 17, 80, 4,
- 0, FB_VMODE_DOUBLE | FB_VMODE_YWRAP
- }, {
- /* dblntsc-ff */
- 640, 400, 640, 400, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 196, 124, 36, 35, 80, 7,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* dblntsc-lace */
- 640, 800, 640, 800, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 196, 124, 72, 70, 80, 14,
- 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- }, {
- /* dblpal */
- 640, 256, 640, 256, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 196, 124, 14, 13, 80, 4,
- 0, FB_VMODE_DOUBLE | FB_VMODE_YWRAP
- }, {
- /* dblpal-ff */
- 640, 512, 640, 512, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 196, 124, 28, 27, 80, 7,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* dblpal-lace */
- 640, 1024, 640, 1024, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 196, 124, 56, 54, 80, 14,
- 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
- },
-
- /*
- * VGA Video Modes
- */
+ /*
+ * AmigaOS Video Modes
+ */
- {
- /* vga */
- 640, 480, 640, 480, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 64, 96, 30, 9, 112, 2,
- 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- }, {
- /* vga70 */
- 640, 400, 640, 400, 0, 0, 4, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, TAG_SHRES, 64, 96, 35, 12, 112, 2,
- FB_SYNC_VERT_HIGH_ACT | FB_SYNC_COMP_HIGH_ACT, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
- },
+ {
+ "ntsc", { /* 640x200, 15 kHz, 60 Hz (NTSC) */
+ 640, 200, 640, 200, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 106, 86, 44, 16, 76, 2,
+ FB_SYNC_BROADCAST, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "ntsc-lace", { /* 640x400, 15 kHz, 60 Hz interlaced (NTSC) */
+ 640, 400, 640, 400, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 106, 86, 88, 33, 76, 4,
+ FB_SYNC_BROADCAST, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "pal", { /* 640x256, 15 kHz, 50 Hz (PAL) */
+ 640, 256, 640, 256, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 106, 86, 40, 14, 76, 2,
+ FB_SYNC_BROADCAST, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "pal-lace", { /* 640x512, 15 kHz, 50 Hz interlaced (PAL) */
+ 640, 512, 640, 512, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 106, 86, 80, 29, 76, 4,
+ FB_SYNC_BROADCAST, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "multiscan", { /* 640x480, 29 kHz, 57 Hz */
+ 640, 480, 640, 480, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 96, 112, 29, 8, 72, 8,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "multiscan-lace", { /* 640x960, 29 kHz, 57 Hz interlaced */
+ 640, 960, 640, 960, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 96, 112, 58, 16, 72, 16,
+ 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "euro36", { /* 640x200, 15 kHz, 72 Hz */
+ 640, 200, 640, 200, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 92, 124, 6, 6, 52, 5,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "euro36-lace", { /* 640x400, 15 kHz, 72 Hz interlaced */
+ 640, 400, 640, 400, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 92, 124, 12, 12, 52, 10,
+ 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "euro72", { /* 640x400, 29 kHz, 68 Hz */
+ 640, 400, 640, 400, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 164, 92, 9, 9, 80, 8,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "euro72-lace", { /* 640x800, 29 kHz, 68 Hz interlaced */
+ 640, 800, 640, 800, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 164, 92, 18, 18, 80, 16,
+ 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "super72", { /* 800x300, 23 kHz, 70 Hz */
+ 800, 300, 800, 300, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 212, 140, 10, 11, 80, 7,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "super72-lace", { /* 800x600, 23 kHz, 70 Hz interlaced */
+ 800, 600, 800, 600, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 212, 140, 20, 22, 80, 14,
+ 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "dblntsc", { /* 640x200, 27 kHz, 57 Hz doublescan */
+ 640, 200, 640, 200, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 196, 124, 18, 17, 80, 4,
+ 0, FB_VMODE_DOUBLE | FB_VMODE_YWRAP
+ }
+ }, {
+ "dblntsc-ff", { /* 640x400, 27 kHz, 57 Hz */
+ 640, 400, 640, 400, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 196, 124, 36, 35, 80, 7,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "dblntsc-lace", { /* 640x800, 27 kHz, 57 Hz interlaced */
+ 640, 800, 640, 800, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 196, 124, 72, 70, 80, 14,
+ 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "dblpal", { /* 640x256, 27 kHz, 47 Hz doublescan */
+ 640, 256, 640, 256, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 196, 124, 14, 13, 80, 4,
+ 0, FB_VMODE_DOUBLE | FB_VMODE_YWRAP
+ }
+ }, {
+ "dblpal-ff", { /* 640x512, 27 kHz, 47 Hz */
+ 640, 512, 640, 512, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 196, 124, 28, 27, 80, 7,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "dblpal-lace", { /* 640x1024, 27 kHz, 47 Hz interlaced */
+ 640, 1024, 640, 1024, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 196, 124, 56, 54, 80, 14,
+ 0, FB_VMODE_INTERLACED | FB_VMODE_YWRAP
+ }
+ },
+
+ /*
+ * VGA Video Modes
+ */
+
+ {
+ "vga", { /* 640x480, 31 kHz, 60 Hz (VGA) */
+ 640, 480, 640, 480, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 64, 96, 30, 9, 112, 2,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "vga70", { /* 640x400, 31 kHz, 70 Hz (VGA) */
+ 640, 400, 640, 400, 0, 0, 4, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_SHRES, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_VERT_HIGH_ACT | FB_SYNC_COMP_HIGH_ACT, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ },
- /*
- * User Defined Video Modes
- */
+#if 0
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }
+ /*
+ * A2024 video modes
+ * These modes don't work yet because there's no A2024 driver.
+ */
+
+ {
+ "a2024-10", { /* 1024x800, 10 Hz */
+ 1024, 800, 1024, 800, 0, 0, 2, 0,
+ {0, 2, 0}, {0, 2, 0}, {0, 2, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 0, 0, 0, 0, 0, 0,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }, {
+ "a2024-15", { /* 1024x800, 15 Hz */
+ 1024, 800, 1024, 800, 0, 0, 2, 0,
+ {0, 2, 0}, {0, 2, 0}, {0, 2, 0}, {0, 0, 0},
+ 0, 0, -1, -1, 0, TAG_HIRES, 0, 0, 0, 0, 0, 0,
+ 0, FB_VMODE_NONINTERLACED | FB_VMODE_YWRAP
+ }
+ }
+#endif
};
-#define NUM_USER_MODES (8)
-#define NUM_TOTAL_MODES arraysize(amiga_fb_predefined)
-#define NUM_PREDEF_MODES (NUM_TOTAL_MODES-NUM_USER_MODES)
+#define NUM_TOTAL_MODES arraysize(amifb_predefined)
static int amifb_ilbm = 0; /* interleaved or normal bitplanes */
-
static int amifb_inverse = 0;
-static int amifb_usermode = 0;
+static int amifb_usermode __initdata = 0;
+static int amifb_userdepth __initdata = -1;
/*
* Some default modes
@@ -1023,6 +990,9 @@ static int amifb_usermode = 0;
#define DEFMODE_AMBER_NTSC "ntsc-lace" /* for flicker fixed NTSC (A3000) */
#define DEFMODE_AGA "vga70" /* for AGA */
+static struct fb_var_screeninfo amifb_default;
+
+
/*
* Macros for the conversion from real world values to hardware register
* values
@@ -1181,40 +1151,47 @@ static u_short sprfetchmode[3] = {
* Interface used by the world
*/
-void amiga_video_setup(char *options, int *ints);
-
-static int amiga_fb_open(int fbidx);
-static int amiga_fb_release(int fbidx);
-static int amiga_fb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int amiga_fb_get_var(struct fb_var_screeninfo *var, int con);
-static int amiga_fb_set_var(struct fb_var_screeninfo *var, int con);
-static int amiga_fb_pan_display(struct fb_var_screeninfo *var, int con);
-static int amiga_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int amiga_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int amiga_fb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con);
-
-static int amiga_fb_get_fix_cursorinfo(struct fb_fix_cursorinfo *fix, int con);
-static int amiga_fb_get_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con);
-static int amiga_fb_set_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con);
-static int amiga_fb_get_cursorstate(struct fb_cursorstate *state, int con);
-static int amiga_fb_set_cursorstate(struct fb_cursorstate *state, int con);
+void amifb_setup(char *options, int *ints);
+
+static int amifb_open(struct fb_info *info);
+static int amifb_release(struct fb_info *info);
+static int amifb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int amifb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int amifb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int amifb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int amifb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int amifb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int amifb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info);
+
+static int amifb_get_fix_cursorinfo(struct fb_fix_cursorinfo *fix, int con);
+static int amifb_get_var_cursorinfo(struct fb_var_cursorinfo *var,
+ u_char *data, int con);
+static int amifb_set_var_cursorinfo(struct fb_var_cursorinfo *var,
+ u_char *data, int con);
+static int amifb_get_cursorstate(struct fb_cursorstate *state, int con);
+static int amifb_set_cursorstate(struct fb_cursorstate *state, int con);
/*
* Interface to the low level console driver
*/
-unsigned long amiga_fb_init(unsigned long mem_start);
-static int amifbcon_switch(int con);
-static int amifbcon_updatevar(int con);
-static void amifbcon_blank(int blank);
-static int amifbcon_setcmap(struct fb_cmap *cmap, int con);
+unsigned long amifb_init(unsigned long mem_start);
+static int amifbcon_switch(int con, struct fb_info *info);
+static int amifbcon_updatevar(int con, struct fb_info *info);
+static void amifbcon_blank(int blank, struct fb_info *info);
/*
* Internal routines
*/
-static void do_install_cmap(int con);
+static void do_install_cmap(int con, struct fb_info *info);
static int flash_cursor(void);
static void amifb_interrupt(int irq, void *dev_id, struct pt_regs *fp);
static void get_video_mode(const char *name);
@@ -1227,22 +1204,22 @@ static char *strtoke(char *s,const char *ct);
*/
static int ami_encode_fix(struct fb_fix_screeninfo *fix,
- struct amiga_fb_par *par);
+ struct amifb_par *par);
static int ami_decode_var(struct fb_var_screeninfo *var,
- struct amiga_fb_par *par);
+ struct amifb_par *par);
static int ami_encode_var(struct fb_var_screeninfo *var,
- struct amiga_fb_par *par);
-static void ami_get_par(struct amiga_fb_par *par);
+ struct amifb_par *par);
+static void ami_get_par(struct amifb_par *par);
static void ami_set_var(struct fb_var_screeninfo *var);
#ifdef DEBUG
-static void ami_set_par(struct amiga_fb_par *par);
+static void ami_set_par(struct amifb_par *par);
#endif
static void ami_pan_var(struct fb_var_screeninfo *var);
static int ami_update_par(void);
static int ami_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp);
+ u_int *transp, struct fb_info *info);
static int ami_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp);
+ u_int transp, struct fb_info *info);
static void ami_update_display(void);
static void ami_init_display(void);
static void ami_do_blank(void);
@@ -1265,29 +1242,14 @@ static void ami_rebuild_copper(void);
extern unsigned short ami_intena_vals[];
-static struct fb_ops amiga_fb_ops = {
- amiga_fb_open, amiga_fb_release, amiga_fb_get_fix, amiga_fb_get_var,
- amiga_fb_set_var, amiga_fb_get_cmap, amiga_fb_set_cmap,
- amiga_fb_pan_display, amiga_fb_ioctl
+static struct fb_ops amifb_ops = {
+ amifb_open, amifb_release, amifb_get_fix, amifb_get_var,
+ amifb_set_var, amifb_get_cmap, amifb_set_cmap,
+ amifb_pan_display, NULL, amifb_ioctl
};
-struct useropts {
- long xres;
- long yres;
- long xres_virtual;
- long yres_virtual;
- long bits_per_pixel;
- long left_margin;
- long right_margin;
- long upper_margin;
- long lower_margin;
- long hsync_len;
- long vsync_len;
-} useropts __initdata = {
- -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1
-};
-__initfunc(void amiga_video_setup(char *options, int *ints))
+__initfunc(void amifb_setup(char *options, int *ints))
{
char *this_opt;
char mcap_spec[80];
@@ -1313,51 +1275,51 @@ __initfunc(void amiga_video_setup(char *options, int *ints))
else if (!strncmp(this_opt, "fstart:", 7))
min_fstrt = simple_strtoul(this_opt+7, NULL, 0);
else if (!strncmp(this_opt, "depth:", 6))
- useropts.bits_per_pixel = simple_strtoul(this_opt+6, NULL, 0);
+ amifb_userdepth = simple_strtoul(this_opt+6, NULL, 0);
else if (!strncmp(this_opt, "size:", 5)) {
p = this_opt + 5;
if (*p != ';')
- useropts.xres = simple_strtoul(p, NULL, 0);
+ amifb_default.xres = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p != ';')
- useropts.yres = simple_strtoul(p, NULL, 0);
+ amifb_default.yres = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p != ';')
- useropts.xres_virtual = simple_strtoul(p, NULL, 0);
+ amifb_default.xres_virtual = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p != ';')
- useropts.yres_virtual = simple_strtoul(p, NULL, 0);
+ amifb_default.yres_virtual = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p)
- useropts.bits_per_pixel = simple_strtoul(p, NULL, 0);
+ amifb_default.bits_per_pixel = simple_strtoul(p, NULL, 0);
} else if (!strncmp(this_opt, "timing:", 7)) {
p = this_opt + 7;
if (*p != ';')
- useropts.left_margin = simple_strtoul(p, NULL, 0);
+ amifb_default.left_margin = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p != ';')
- useropts.right_margin = simple_strtoul(p, NULL, 0);
+ amifb_default.right_margin = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p != ';')
- useropts.upper_margin = simple_strtoul(p, NULL, 0);
+ amifb_default.upper_margin = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p)
- useropts.lower_margin = simple_strtoul(p, NULL, 0);
+ amifb_default.lower_margin = simple_strtoul(p, NULL, 0);
} else if (!strncmp(this_opt, "sync:", 5)) {
p = this_opt + 5;
if (*p != ';')
- useropts.hsync_len = simple_strtoul(p, NULL, 0);
+ amifb_default.hsync_len = simple_strtoul(p, NULL, 0);
if (!(p = strchr(p, ';')))
continue;
if (*++p)
- useropts.vsync_len = simple_strtoul(p, NULL, 0);
+ amifb_default.vsync_len = simple_strtoul(p, NULL, 0);
} else
get_video_mode(this_opt);
}
@@ -1395,10 +1357,10 @@ __initfunc(void amiga_video_setup(char *options, int *ints))
if (hmax <= 0 || hmax <= hmin)
goto cap_invalid;
- vfmin = vmin;
- vfmax = vmax;
- hfmin = hmin;
- hfmax = hmax;
+ fb_info.monspecs.vfmin = vmin;
+ fb_info.monspecs.vfmax = vmax;
+ fb_info.monspecs.hfmin = hmin;
+ fb_info.monspecs.hfmax = hmax;
cap_invalid:
;
}
@@ -1408,7 +1370,7 @@ cap_invalid:
* Open/Release the frame buffer device
*/
-static int amiga_fb_open(int fbidx)
+static int amifb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -1418,7 +1380,7 @@ static int amiga_fb_open(int fbidx)
return(0);
}
-static int amiga_fb_release(int fbidx)
+static int amifb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return(0);
@@ -1429,9 +1391,10 @@ static int amiga_fb_release(int fbidx)
* Get the Fixed Part of the Display
*/
-static int amiga_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
+static int amifb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
{
- struct amiga_fb_par par;
+ struct amifb_par par;
if (con == -1)
ami_get_par(&par);
@@ -1448,12 +1411,13 @@ static int amiga_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
* Get the User Defined Part of the Display
*/
-static int amiga_fb_get_var(struct fb_var_screeninfo *var, int con)
+static int amifb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
int err = 0;
if (con == -1) {
- struct amiga_fb_par par;
+ struct amifb_par par;
ami_get_par(&par);
err = ami_encode_var(var, &par);
@@ -1466,11 +1430,12 @@ static int amiga_fb_get_var(struct fb_var_screeninfo *var, int con)
* Set the User Defined Part of the Display
*/
-static int amiga_fb_set_var(struct fb_var_screeninfo *var, int con)
+static int amifb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
int err, activate = var->activate;
int oldxres, oldyres, oldvxres, oldvyres, oldbpp;
- struct amiga_fb_par par;
+ struct amifb_par par;
struct display *display;
if (con >= 0)
@@ -1513,13 +1478,32 @@ static int amiga_fb_set_var(struct fb_var_screeninfo *var, int con)
display->line_length = fix.line_length;
display->can_soft_blank = 1;
display->inverse = amifb_inverse;
+ switch (fix.type) {
+#ifdef CONFIG_FBCON_ILBM
+ case FB_TYPE_INTERLEAVED_PLANES:
+ display->dispsw = &fbcon_ilbm;
+ break;
+#endif
+#ifdef CONFIG_FBCON_AFB
+ case FB_TYPE_PLANES:
+ display->dispsw = &fbcon_afb;
+ break;
+#endif
+#ifdef CONFIG_FBCON_MFB
+ case FB_TYPE_PACKED_PIXELS: /* depth == 1 */
+ display->dispsw = &fbcon_mfb;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ }
if (fb_info.changevar)
(*fb_info.changevar)(con);
}
if (oldbpp != var->bits_per_pixel) {
if ((err = fb_alloc_cmap(&display->cmap, 0, 0)))
return err;
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
if (con == currcon)
ami_set_var(&display->var);
@@ -1533,7 +1517,8 @@ static int amiga_fb_set_var(struct fb_var_screeninfo *var, int con)
* This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
*/
-static int amiga_fb_pan_display(struct fb_var_screeninfo *var, int con)
+static int amifb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
if (var->vmode & FB_VMODE_YWRAP) {
if (var->yoffset<0 || var->yoffset >= fb_display[con].var.yres_virtual || var->xoffset)
@@ -1562,15 +1547,16 @@ static int amiga_fb_pan_display(struct fb_var_screeninfo *var, int con)
* Get the Colormap
*/
-static int amiga_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int amifb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
if (con == currcon) /* current console? */
return fb_get_cmap(cmap, &fb_display[con].var, kspc,
- ami_getcolreg);
+ ami_getcolreg, info);
else if (fb_display[con].cmap.len) /* non default colormap? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return 0;
}
@@ -1579,7 +1565,8 @@ static int amiga_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
* Set the Colormap
*/
-static int amiga_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int amifb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
int err;
@@ -1591,7 +1578,7 @@ static int amiga_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
}
if (con == currcon) /* current console? */
return fb_set_cmap(cmap, &fb_display[con].var, kspc,
- ami_setcolreg);
+ ami_setcolreg, info);
else
fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
return 0;
@@ -1601,8 +1588,8 @@ static int amiga_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
* Amiga Frame Buffer Specific ioctls
*/
-static int amiga_fb_ioctl(struct inode *inode, struct file *file,
- u_int cmd, u_long arg, int con)
+static int amifb_ioctl(struct inode *inode, struct file *file,
+ u_int cmd, u_long arg, int con, struct fb_info *info)
{
int i;
@@ -1612,7 +1599,7 @@ static int amiga_fb_ioctl(struct inode *inode, struct file *file,
i = verify_area(VERIFY_WRITE, (void *)arg, sizeof(crsrfix));
if (!i) {
- i = amiga_fb_get_fix_cursorinfo(&crsrfix, con);
+ i = amifb_get_fix_cursorinfo(&crsrfix, con);
copy_to_user((void *)arg, &crsrfix, sizeof(crsrfix));
}
return i;
@@ -1622,7 +1609,7 @@ static int amiga_fb_ioctl(struct inode *inode, struct file *file,
i = verify_area(VERIFY_WRITE, (void *)arg, sizeof(crsrvar));
if (!i) {
- i = amiga_fb_get_var_cursorinfo(&crsrvar,
+ i = amifb_get_var_cursorinfo(&crsrvar,
((struct fb_var_cursorinfo *)arg)->data, con);
copy_to_user((void *)arg, &crsrvar, sizeof(crsrvar));
}
@@ -1634,7 +1621,7 @@ static int amiga_fb_ioctl(struct inode *inode, struct file *file,
i = verify_area(VERIFY_READ, (void *)arg, sizeof(crsrvar));
if (!i) {
copy_from_user(&crsrvar, (void *)arg, sizeof(crsrvar));
- i = amiga_fb_set_var_cursorinfo(&crsrvar,
+ i = amifb_set_var_cursorinfo(&crsrvar,
((struct fb_var_cursorinfo *)arg)->data, con);
}
return i;
@@ -1644,7 +1631,7 @@ static int amiga_fb_ioctl(struct inode *inode, struct file *file,
i = verify_area(VERIFY_WRITE, (void *)arg, sizeof(crsrstate));
if (!i) {
- i = amiga_fb_get_cursorstate(&crsrstate, con);
+ i = amifb_get_cursorstate(&crsrstate, con);
copy_to_user((void *)arg, &crsrstate, sizeof(crsrstate));
}
return i;
@@ -1655,27 +1642,27 @@ static int amiga_fb_ioctl(struct inode *inode, struct file *file,
i = verify_area(VERIFY_READ, (void *)arg, sizeof(crsrstate));
if (!i) {
copy_from_user(&crsrstate, (void *)arg, sizeof(crsrstate));
- i = amiga_fb_set_cursorstate(&crsrstate, con);
+ i = amifb_set_cursorstate(&crsrstate, con);
}
return i;
}
#ifdef DEBUG
case FBCMD_GET_CURRENTPAR : {
- struct amiga_fb_par par;
+ struct amifb_par par;
- i = verify_area(VERIFY_WRITE, (void *)arg, sizeof(struct amiga_fb_par));
+ i = verify_area(VERIFY_WRITE, (void *)arg, sizeof(struct amifb_par));
if (!i) {
ami_get_par(&par);
- copy_to_user((void *)arg, &par, sizeof(struct amiga_fb_par));
+ copy_to_user((void *)arg, &par, sizeof(struct amifb_par));
}
return i;
}
case FBCMD_SET_CURRENTPAR : {
- struct amiga_fb_par par;
+ struct amifb_par par;
- i = verify_area(VERIFY_READ, (void *)arg, sizeof(struct amiga_fb_par));
+ i = verify_area(VERIFY_READ, (void *)arg, sizeof(struct amifb_par));
if (!i) {
- copy_from_user(&par, (void *)arg, sizeof(struct amiga_fb_par));
+ copy_from_user(&par, (void *)arg, sizeof(struct amifb_par));
ami_set_par(&par);
}
return i;
@@ -1689,27 +1676,27 @@ static int amiga_fb_ioctl(struct inode *inode, struct file *file,
* Hardware Cursor
*/
-static int amiga_fb_get_fix_cursorinfo(struct fb_fix_cursorinfo *fix, int con)
+static int amifb_get_fix_cursorinfo(struct fb_fix_cursorinfo *fix, int con)
{
return ami_get_fix_cursorinfo(fix, con);
}
-static int amiga_fb_get_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con)
+static int amifb_get_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con)
{
return ami_get_var_cursorinfo(var, data, con);
}
-static int amiga_fb_set_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con)
+static int amifb_set_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con)
{
return ami_set_var_cursorinfo(var, data, con);
}
-static int amiga_fb_get_cursorstate(struct fb_cursorstate *state, int con)
+static int amifb_get_cursorstate(struct fb_cursorstate *state, int con)
{
return ami_get_cursorstate(state, con);
}
-static int amiga_fb_set_cursorstate(struct fb_cursorstate *state, int con)
+static int amifb_set_cursorstate(struct fb_cursorstate *state, int con)
{
return ami_set_cursorstate(state, con);
}
@@ -1719,7 +1706,7 @@ static int amiga_fb_set_cursorstate(struct fb_cursorstate *state, int con)
* Initialisation
*/
-__initfunc(unsigned long amiga_fb_init(unsigned long mem_start))
+__initfunc(unsigned long amifb_init(unsigned long mem_start))
{
int err, tag, i;
u_long chipptr;
@@ -1745,7 +1732,7 @@ __initfunc(unsigned long amiga_fb_init(unsigned long mem_start))
switch (amiga_chipset) {
#ifdef CONFIG_FB_AMIGA_OCS
case CS_OCS:
- strcat(amiga_fb_name, "OCS");
+ strcat(amifb_name, "OCS");
default_chipset:
chipset = TAG_OCS;
maxdepth[TAG_SHRES] = 0; /* OCS means no SHRES */
@@ -1761,7 +1748,7 @@ default_chipset:
#ifdef CONFIG_FB_AMIGA_ECS
case CS_ECS:
- strcat(amiga_fb_name, "ECS");
+ strcat(amifb_name, "ECS");
chipset = TAG_ECS;
maxdepth[TAG_SHRES] = 2;
maxdepth[TAG_HIRES] = 4;
@@ -1785,7 +1772,7 @@ default_chipset:
#ifdef CONFIG_FB_AMIGA_AGA
case CS_AGA:
- strcat(amiga_fb_name, "AGA");
+ strcat(amifb_name, "AGA");
chipset = TAG_AGA;
maxdepth[TAG_SHRES] = 8;
maxdepth[TAG_HIRES] = 8;
@@ -1804,7 +1791,7 @@ default_chipset:
default:
#ifdef CONFIG_FB_AMIGA_OCS
printk("Unknown graphics chipset, defaulting to OCS\n");
- strcat(amiga_fb_name, "Unknown");
+ strcat(amifb_name, "Unknown");
goto default_chipset;
#else /* CONFIG_FB_AMIGA_OCS */
return mem_start;
@@ -1824,26 +1811,42 @@ default_chipset:
* Replace the Tag Values with the Real Pixel Clock Values
*/
- for (i = 0; i < NUM_PREDEF_MODES; i++) {
- tag = amiga_fb_predefined[i].pixclock;
+ if (amifb_userdepth != -1)
+ amifb_default.bits_per_pixel = amifb_userdepth;
+ for (i = 0; i < NUM_TOTAL_MODES; i++) {
+ struct fb_var_screeninfo *var = &amifb_predefined[i].var;
+ tag = var->pixclock;
if (tag == TAG_SHRES || tag == TAG_HIRES || tag == TAG_LORES) {
- amiga_fb_predefined[i].pixclock = pixclock[tag];
- if (amiga_fb_predefined[i].bits_per_pixel > maxdepth[tag])
- amiga_fb_predefined[i].bits_per_pixel = maxdepth[tag];
+ var->pixclock = pixclock[tag];
+ if (var->bits_per_pixel > maxdepth[tag])
+ var->bits_per_pixel = maxdepth[tag];
}
}
+ tag = amifb_default.pixclock;
+ if (tag == TAG_SHRES || tag == TAG_HIRES || tag == TAG_LORES) {
+ amifb_default.pixclock = pixclock[tag];
+ if (amifb_default.bits_per_pixel > maxdepth[tag])
+ amifb_default.bits_per_pixel = maxdepth[tag];
+ }
+
+ /*
+ * These monitor specs are for a typical Amiga monitor (e.g. A1960)
+ */
+ if (fb_info.monspecs.hfmin == 0) {
+ fb_info.monspecs.hfmin = 15000;
+ fb_info.monspecs.hfmax = 38000;
+ fb_info.monspecs.vfmin = 49;
+ fb_info.monspecs.vfmax = 90;
+ }
- strcpy(fb_info.modename, amiga_fb_name);
+ strcpy(fb_info.modename, amifb_name);
fb_info.changevar = NULL;
fb_info.node = -1;
- fb_info.fbops = &amiga_fb_ops;
- fb_info.fbvar_num = NUM_TOTAL_MODES;
- fb_info.fbvar = amiga_fb_predefined;
+ fb_info.fbops = &amifb_ops;
fb_info.disp = &disp;
fb_info.switch_con = &amifbcon_switch;
fb_info.updatevar = &amifbcon_updatevar;
fb_info.blank = &amifbcon_blank;
- fb_info.setcmap = &amifbcon_setcmap;
err = register_framebuffer(&fb_info);
if (err < 0)
@@ -1889,10 +1892,11 @@ default_chipset:
custom.intena = IF_VERTB;
custom.intena = IF_SETCLR | IF_COPER;
- amiga_fb_set_var(&amiga_fb_predefined[0], -1);
+ amifb_set_var(&amifb_default, -1, &fb_info);
- printk("%s frame buffer device, using %ldK of video memory\n",
- fb_info.modename, videomemorysize>>10);
+ printk("fb%d: %s frame buffer device, using %ldK of video memory\n",
+ GET_FB_IDX(fb_info.node), fb_info.modename,
+ videomemorysize>>10);
/* TODO: This driver cannot be unloaded yet */
MOD_INC_USE_COUNT;
@@ -1900,17 +1904,17 @@ default_chipset:
return mem_start;
}
-static int amifbcon_switch(int con)
+static int amifbcon_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap,
- &fb_display[currcon].var, 1, ami_getcolreg);
+ &fb_display[currcon].var, 1, ami_getcolreg, info);
currcon = con;
ami_set_var(&fb_display[con].var);
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return 0;
}
@@ -1918,7 +1922,7 @@ static int amifbcon_switch(int con)
* Update the `var' structure (called by fbcon.c)
*/
-static int amifbcon_updatevar(int con)
+static int amifbcon_updatevar(int con, struct fb_info *info)
{
ami_pan_var(&fb_display[con].var);
return 0;
@@ -1928,7 +1932,7 @@ static int amifbcon_updatevar(int con)
* Blank the display.
*/
-static void amifbcon_blank(int blank)
+static void amifbcon_blank(int blank, struct fb_info *info)
{
do_blank = blank ? blank : -1;
}
@@ -1937,23 +1941,17 @@ static void amifbcon_blank(int blank)
* Set the colormap
*/
-static int amifbcon_setcmap(struct fb_cmap *cmap, int con)
-{
- return(amiga_fb_set_cmap(cmap, 1, con));
-}
-
-
-static void do_install_cmap(int con)
+static void do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
- ami_setcolreg);
+ ami_setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
&fb_display[con].var, 1,
- ami_setcolreg);
+ ami_setcolreg, info);
}
static int flash_cursor(void)
@@ -2039,33 +2037,9 @@ __initfunc(static void get_video_mode(const char *name))
{
int i;
- for (i = 1; i < NUM_PREDEF_MODES; i++) {
- if (!strcmp(name, amiga_fb_modenames[i])) {
- amiga_fb_predefined[0] = amiga_fb_predefined[i];
-
- if (useropts.xres != -1)
- amiga_fb_predefined[0].xres = useropts.xres;
- if (useropts.yres != -1)
- amiga_fb_predefined[0].yres = useropts.yres;
- if (useropts.xres_virtual != -1)
- amiga_fb_predefined[0].xres_virtual = useropts.xres_virtual;
- if (useropts.yres_virtual != -1)
- amiga_fb_predefined[0].yres_virtual = useropts.yres_virtual;
- if (useropts.bits_per_pixel != -1)
- amiga_fb_predefined[0].bits_per_pixel = useropts.bits_per_pixel;
- if (useropts.left_margin != -1)
- amiga_fb_predefined[0].left_margin = useropts.left_margin;
- if (useropts.right_margin != -1)
- amiga_fb_predefined[0].right_margin = useropts.right_margin;
- if (useropts.upper_margin != -1)
- amiga_fb_predefined[0].upper_margin = useropts.upper_margin;
- if (useropts.lower_margin != -1)
- amiga_fb_predefined[0].lower_margin = useropts.lower_margin;
- if (useropts.hsync_len != -1)
- amiga_fb_predefined[0].hsync_len = useropts.hsync_len;
- if (useropts.vsync_len != -1)
- amiga_fb_predefined[0].vsync_len = useropts.vsync_len;
-
+ for (i = 0; i < NUM_TOTAL_MODES; i++) {
+ if (!strcmp(name, amifb_predefined[i].name)) {
+ amifb_default = amifb_predefined[i].var;
amifb_usermode = i;
return;
}
@@ -2073,23 +2047,22 @@ __initfunc(static void get_video_mode(const char *name))
}
/*
- * Probe the Video Modes
+ * Probe the Video Modes
*/
__initfunc(static void check_default_mode(void))
{
- struct amiga_fb_par par;
+ struct amifb_par par;
int mode;
- for (mode = 0; mode < NUM_PREDEF_MODES; mode++) {
- if (!ami_decode_var(&amiga_fb_predefined[mode], &par)) {
- if (mode)
- amiga_fb_predefined[0] = amiga_fb_predefined[mode];
+ if (!ami_decode_var(&amifb_default, &par))
+ return;
+ printk("Can't use default video mode. Probing video modes...\n");
+ for (mode = 0; mode < NUM_TOTAL_MODES; mode++)
+ if (!ami_decode_var(&amifb_predefined[mode].var, &par)) {
+ amifb_default = amifb_predefined[mode].var;
return;
}
- if (!mode)
- printk("Can't use default video mode. Probing video modes...\n");
- }
panic("Can't find any usable video mode");
}
@@ -2141,13 +2114,19 @@ __initfunc(static char *strtoke(char *s,const char *ct))
*/
static int ami_encode_fix(struct fb_fix_screeninfo *fix,
- struct amiga_fb_par *par)
+ struct amifb_par *par)
{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
- strcpy(fix->id, amiga_fb_name);
+ strcpy(fix->id, amifb_name);
fix->smem_start = (char *)videomemory;
fix->smem_len = videomemorysize;
+#ifdef CONFIG_FBCON_MFB
+ if (par->bpp == 1) {
+ fix->type = FB_TYPE_PACKED_PIXELS;
+ fix->type_aux = 0;
+ } else
+#endif
if (amifb_ilbm) {
fix->type = FB_TYPE_INTERLEAVED_PLANES;
fix->type_aux = par->next_line;
@@ -2169,6 +2148,7 @@ static int ami_encode_fix(struct fb_fix_screeninfo *fix,
fix->xpanstep = 16<<maxfmode;
fix->ypanstep = 1;
}
+ fix->accel = FB_ACCEL_AMIGABLITT;
return 0;
}
@@ -2178,11 +2158,11 @@ static int ami_encode_fix(struct fb_fix_screeninfo *fix,
*/
static int ami_decode_var(struct fb_var_screeninfo *var,
- struct amiga_fb_par *par)
+ struct amifb_par *par)
{
u_short clk_shift, line_shift;
u_long maxfetchstop, fstrt, fsize, fconst, xres_n, yres_n;
- u_long hrate = 0, vrate = 0;
+ u_int htotal, vtotal;
/*
* Find a matching Pixel Clock
@@ -2319,8 +2299,8 @@ static int ami_decode_var(struct fb_var_screeninfo *var,
DPRINTK("diwstrt_v too low for pal\n");
return -EINVAL;
}
- hrate = 15625;
- vrate = 50;
+ htotal = PAL_HTOTAL>>clk_shift;
+ vtotal = PAL_VTOTAL>>1;
if (!IS_OCS) {
par->beamcon0 = BMC0_PAL;
par->bplcon3 |= BPC3_BRDRBLNK;
@@ -2349,8 +2329,8 @@ static int ami_decode_var(struct fb_var_screeninfo *var,
DPRINTK("diwstrt_v too low for ntsc\n");
return -EINVAL;
}
- hrate = 15750;
- vrate = 60;
+ htotal = NTSC_HTOTAL>>clk_shift;
+ vtotal = NTSC_VTOTAL>>1;
if (!IS_OCS) {
par->beamcon0 = 0;
par->bplcon3 |= BPC3_BRDRBLNK;
@@ -2409,9 +2389,8 @@ static int ami_decode_var(struct fb_var_screeninfo *var,
par->beamcon0 |= BMC0_VSYTRUE;
if (var->sync & FB_SYNC_COMP_HIGH_ACT)
par->beamcon0 |= BMC0_CSYTRUE;
- hrate = (amiga_masterclock+par->htotal/2)/par->htotal;
- vrate = div2(par->vtotal) * par->htotal;
- vrate = (amiga_masterclock+vrate/2)/vrate;
+ htotal = par->htotal>>clk_shift;
+ vtotal = par->vtotal>>1;
} else {
DPRINTK("only broadcast modes possible for ocs\n");
return -EINVAL;
@@ -2546,7 +2525,8 @@ static int ami_decode_var(struct fb_var_screeninfo *var,
par->crsr.spot_x = par->crsr.spot_y = 0;
par->crsr.height = par->crsr.width = 0;
- if (hrate < hfmin || hrate > hfmax || vrate < vfmin || vrate > vfmax) {
+ if (!fbmon_valid_timings(pixclock[clk_shift], htotal, vtotal,
+ &fb_info)) {
DPRINTK("mode doesn't fit for monitor\n");
return -EINVAL;
}
@@ -2560,7 +2540,7 @@ static int ami_decode_var(struct fb_var_screeninfo *var,
*/
static int ami_encode_var(struct fb_var_screeninfo *var,
- struct amiga_fb_par *par)
+ struct amifb_par *par)
{
u_short clk_shift, line_shift;
int i;
@@ -2606,7 +2586,6 @@ static int ami_encode_var(struct fb_var_screeninfo *var,
var->height = -1;
var->width = -1;
- var->accel = 0;
var->pixclock = pixclock[clk_shift];
@@ -2657,7 +2636,7 @@ static int ami_encode_var(struct fb_var_screeninfo *var,
* Get current hardware setting
*/
-static void ami_get_par(struct amiga_fb_par *par)
+static void ami_get_par(struct amifb_par *par)
{
*par = currentpar;
}
@@ -2676,7 +2655,7 @@ static void ami_set_var(struct fb_var_screeninfo *var)
}
#ifdef DEBUG
-static void ami_set_par(struct amiga_fb_par *par)
+static void ami_set_par(struct amifb_par *par)
{
do_vmode_pan = 0;
do_vmode_full = 0;
@@ -2695,7 +2674,7 @@ static void ami_set_par(struct amiga_fb_par *par)
static void ami_pan_var(struct fb_var_screeninfo *var)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
par->xoffset = var->xoffset;
par->yoffset = var->yoffset;
@@ -2715,7 +2694,7 @@ static void ami_pan_var(struct fb_var_screeninfo *var)
static int ami_update_par(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
short clk_shift, vshift, fstrt, fsize, fstop, fconst, shift, move, mod;
clk_shift = par->clk_shift;
@@ -2780,7 +2759,7 @@ static int ami_update_par(void)
*/
static int ami_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp)
+ u_int *transp, struct fb_info *info)
{
if (IS_AGA) {
if (regno > 255)
@@ -2804,7 +2783,7 @@ static int ami_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
*/
static int ami_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp)
+ u_int transp, struct fb_info *info)
{
#if defined(CONFIG_FB_AMIGA_AGA)
u_short bplcon3 = currentpar.bplcon3;
@@ -2867,7 +2846,7 @@ static int ami_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
static void ami_update_display(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
custom.bplcon1 = par->bplcon1;
custom.bpl1mod = par->bpl1mod;
@@ -2882,7 +2861,7 @@ static void ami_update_display(void)
static void ami_init_display(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
custom.bplcon0 = par->bplcon0 & ~BPC0_LACE;
custom.bplcon2 = (IS_OCS ? 0 : BPC2_KILLEHB) | BPC2_PF2P2 | BPC2_PF1P2;
@@ -2938,7 +2917,7 @@ static void ami_init_display(void)
static void ami_do_blank(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
#if defined(CONFIG_FB_AMIGA_AGA)
u_short bplcon3 = par->bplcon3;
#endif
@@ -3023,7 +3002,7 @@ static void ami_do_blank(void)
static int ami_get_fix_cursorinfo(struct fb_fix_cursorinfo *fix, int con)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
fix->crsr_width = fix->crsr_xsize = par->crsr.width;
fix->crsr_height = fix->crsr_ysize = par->crsr.height;
@@ -3034,7 +3013,7 @@ static int ami_get_fix_cursorinfo(struct fb_fix_cursorinfo *fix, int con)
static int ami_get_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
register u_short *lspr, *sspr;
#ifdef __mc68000__
register u_long datawords asm ("d2");
@@ -3109,7 +3088,7 @@ static int ami_get_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, i
static int ami_set_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, int con)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
register u_short *lspr, *sspr;
#ifdef __mc68000__
register u_long datawords asm ("d2");
@@ -3228,7 +3207,7 @@ static int ami_set_var_cursorinfo(struct fb_var_cursorinfo *var, u_char *data, i
static int ami_get_cursorstate(struct fb_cursorstate *state, int con)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
state->xoffset = par->crsr.crsr_x;
state->yoffset = par->crsr.crsr_y;
@@ -3238,7 +3217,7 @@ static int ami_get_cursorstate(struct fb_cursorstate *state, int con)
static int ami_set_cursorstate(struct fb_cursorstate *state, int con)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
par->crsr.crsr_x = state->xoffset;
par->crsr.crsr_y = state->yoffset;
@@ -3250,7 +3229,7 @@ static int ami_set_cursorstate(struct fb_cursorstate *state, int con)
static void ami_set_sprite(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
copins *copl, *cops;
u_short hs, vs, ve;
u_long pl, ps, pt;
@@ -3333,7 +3312,7 @@ __initfunc(static void ami_init_copper(void))
static void ami_reinit_copper(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
copdisplay.init[cip_bplcon0].w[1] = ~(BPC0_BPU3 | BPC0_BPU2 | BPC0_BPU1 | BPC0_BPU0) & par->bplcon0;
copdisplay.wait->l = CWAIT(32, par->diwstrt_v-4);
@@ -3345,7 +3324,7 @@ static void ami_reinit_copper(void)
static void ami_build_copper(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
copins *copl, *cops;
u_long p;
@@ -3422,7 +3401,7 @@ static void ami_build_copper(void)
static void ami_rebuild_copper(void)
{
- struct amiga_fb_par *par = &currentpar;
+ struct amifb_par *par = &currentpar;
copins *copl, *cops;
u_short line, h_end1, h_end2;
short i;
@@ -3507,7 +3486,7 @@ static void ami_rebuild_copper(void)
#ifdef MODULE
int init_module(void)
{
- return(amiga_fb_init(NULL));
+ return(amifb_init(NULL));
}
void cleanup_module(void)
diff --git a/drivers/video/atafb.c b/drivers/video/atafb.c
index ada071f2b..ff7aedfe7 100644
--- a/drivers/video/atafb.c
+++ b/drivers/video/atafb.c
@@ -66,10 +66,31 @@
#include <asm/atarihw.h>
#include <asm/atariints.h>
+#include <asm/atari_stram.h>
#include <linux/fb.h>
#include <asm/atarikb.h>
+#ifdef CONFIG_FBCON_CFB8
+#include "fbcon-cfb8.h"
+#endif
+#ifdef CONFIG_FBCON_CFB16
+#include "fbcon-cfb16.h"
+#endif
+#ifdef CONFIG_FBCON_IPLAN2P2
+#include "fbcon-iplan2p2.h"
+#endif
+#ifdef CONFIG_FBCON_IPLAN2P4
+#include "fbcon-iplan2p4.h"
+#endif
+#ifdef CONFIG_FBCON_IPLAN2P8
+#include "fbcon-iplan2p8.h"
+#endif
+#ifdef CONFIG_FBCON_MFB
+#include "fbcon-mfb.h"
+#endif
+
+
#define SWITCH_ACIA 0x01 /* modes for switch on OverScan */
#define SWITCH_SND6 0x40
#define SWITCH_SND7 0x80
@@ -92,16 +113,18 @@ static int use_hwscroll = 1;
static int sttt_xres=640,st_yres=400,tt_yres=480;
static int sttt_xres_virtual=640,sttt_yres_virtual=400;
static int ovsc_offset=0, ovsc_addlen=0;
-int ovsc_switchmode=0;
-static struct atari_fb_par {
+static struct atafb_par {
unsigned long screen_base;
int yres_virtual;
+#if defined ATAFB_TT || defined ATAFB_STE
union {
struct {
int mode;
int sync;
} tt, st;
+#endif
+#ifdef ATAFB_FALCON
struct falcon_hw {
/* Here are fields for storing a video mode, as direct
* parameters for the hardware.
@@ -121,6 +144,7 @@ static struct atari_fb_par {
short ste_mode;
short bpp;
} falcon;
+#endif
/* Nothing needed for external mode */
} hw;
} current_par;
@@ -130,6 +154,7 @@ static struct atari_fb_par {
* hardware extensions (e.g. ScreenBlaster) */
static int DontCalcRes = 0;
+#ifdef ATAFB_FALCON
#define HHT hw.falcon.hht
#define HBB hw.falcon.hbb
#define HBE hw.falcon.hbe
@@ -150,6 +175,7 @@ static int DontCalcRes = 0;
#define VMO_DOUBLE 0x01
#define VMO_INTER 0x02
#define VMO_PREMASK 0x0c
+#endif
static struct fb_info fb_info;
@@ -239,26 +265,22 @@ extern int fontheight_8x16;
extern int fontwidth_8x16;
extern unsigned char fontdata_8x16[];
-/* import first 16 colors from fbcon.c */
-extern unsigned short packed16_cmap[16];
-
-
/* ++roman: This structure abstracts from the underlying hardware (ST(e),
* TT, or Falcon.
*
* int (*detect)( void )
* This function should detect the current video mode settings and
- * store them in atari_fb_predefined[0] for later reference by the
+ * store them in atafb_predefined[0] for later reference by the
* user. Return the index+1 of an equivalent predefined mode or 0
* if there is no such.
*
* int (*encode_fix)( struct fb_fix_screeninfo *fix,
- * struct atari_fb_par *par )
+ * struct atafb_par *par )
* This function should fill in the 'fix' structure based on the
* values in the 'par' structure.
*
* int (*decode_var)( struct fb_var_screeninfo *var,
- * struct atari_fb_par *par )
+ * struct atafb_par *par )
* Get the video params out of 'var'. If a value doesn't fit, round
* it up, if it's too big, return EINVAL.
* Round up in the following order: bits_per_pixel, xres, yres,
@@ -266,26 +288,26 @@ extern unsigned short packed16_cmap[16];
* horizontal timing, vertical timing.
*
* int (*encode_var)( struct fb_var_screeninfo *var,
- * struct atari_fb_par *par );
+ * struct atafb_par *par );
* Fill the 'var' structure based on the values in 'par' and maybe
* other values read out of the hardware.
*
- * void (*get_par)( struct atari_fb_par *par )
+ * void (*get_par)( struct atafb_par *par )
* Fill the hardware's 'par' structure.
*
- * void (*set_par)( struct atari_fb_par *par )
+ * void (*set_par)( struct atafb_par *par )
* Set the hardware according to 'par'.
*
* int (*setcolreg)( unsigned regno, unsigned red,
* unsigned green, unsigned blue,
- * unsigned transp )
+ * unsigned transp, struct fb_info *info )
* Set a single color register. The values supplied are already
* rounded down to the hardware's capabilities (according to the
* entries in the var structure). Return != 0 for invalid regno.
*
* int (*getcolreg)( unsigned regno, unsigned *red,
* unsigned *green, unsigned *blue,
- * unsigned *transp )
+ * unsigned *transp, struct fb_info *info )
* Read a single color register and split it into
* colors/transparent. Return != 0 for invalid regno.
*
@@ -305,23 +327,23 @@ extern unsigned short packed16_cmap[16];
static struct fb_hwswitch {
int (*detect)( void );
int (*encode_fix)( struct fb_fix_screeninfo *fix,
- struct atari_fb_par *par );
+ struct atafb_par *par );
int (*decode_var)( struct fb_var_screeninfo *var,
- struct atari_fb_par *par );
+ struct atafb_par *par );
int (*encode_var)( struct fb_var_screeninfo *var,
- struct atari_fb_par *par );
- void (*get_par)( struct atari_fb_par *par );
- void (*set_par)( struct atari_fb_par *par );
+ struct atafb_par *par );
+ void (*get_par)( struct atafb_par *par );
+ void (*set_par)( struct atafb_par *par );
int (*getcolreg)( unsigned regno, unsigned *red,
unsigned *green, unsigned *blue,
- unsigned *transp );
+ unsigned *transp, struct fb_info *info );
int (*setcolreg)( unsigned regno, unsigned red,
unsigned green, unsigned blue,
- unsigned transp );
+ unsigned transp, struct fb_info *info );
void (*set_screen_base)( unsigned long s_base );
int (*blank)( int blank_mode );
int (*pan_display)( struct fb_var_screeninfo *var,
- struct atari_fb_par *par);
+ struct atafb_par *par);
} *fbhw;
static char *autodetect_names[] = {"autodetect", NULL};
@@ -337,15 +359,6 @@ static char *vga16_names[] = {"vga16", "default3", NULL};
static char *vga256_names[] = {"vga256", NULL};
static char *falh2_names[] = {"falh2", NULL};
static char *falh16_names[] = {"falh16", NULL};
-static char *user0_names[] = {"user0", NULL};
-static char *user1_names[] = {"user1", NULL};
-static char *user2_names[] = {"user2", NULL};
-static char *user3_names[] = {"user3", NULL};
-static char *user4_names[] = {"user4", NULL};
-static char *user5_names[] = {"user5", NULL};
-static char *user6_names[] = {"user6", NULL};
-static char *user7_names[] = {"user7", NULL};
-static char *dummy_names[] = {"dummy", NULL};
static char **fb_var_names[] = {
/* Writing the name arrays directly in this array (via "(char *[]){...}")
@@ -365,22 +378,11 @@ static char **fb_var_names[] = {
vga256_names,
falh2_names,
falh16_names,
- dummy_names, dummy_names, dummy_names, dummy_names,
- dummy_names, dummy_names, dummy_names, dummy_names,
- dummy_names, dummy_names,
- user0_names,
- user1_names,
- user2_names,
- user3_names,
- user4_names,
- user5_names,
- user6_names,
- user7_names,
NULL
/* ,NULL */ /* this causes a sigsegv on my gcc-2.5.8 */
};
-static struct fb_var_screeninfo atari_fb_predefined[] = {
+static struct fb_var_screeninfo atafb_predefined[] = {
/*
* yres_virtual==0 means use hw-scrolling if possible, else yres
*/
@@ -436,53 +438,9 @@ static struct fb_var_screeninfo atari_fb_predefined[] = {
896, 608, 896, 0, 0, 0, 4, 0,
{0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- /* Minor 14..23 free for more standard video modes */
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- { 0, },
- /* Minor 24..31 reserved for user defined video modes */
- { /* user0, initialized to Rx;y;d from commandline, if supplied */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user1 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user2 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user3 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user4 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user5 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user6 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 },
- { /* user7 */
- 0, 0, 0, 0, 0, 0, 0, 0,
- {0, 6, 0}, {0, 6, 0}, {0, 6, 0}, {0, 0, 0},
- 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0 }
};
-static int num_atari_fb_predefined=arraysize(atari_fb_predefined);
+static int num_atafb_predefined=arraysize(atafb_predefined);
static int
@@ -492,7 +450,7 @@ get_video_mode(char *vname)
char **name;
int i;
name_list=fb_var_names;
- for (i = 0 ; i < num_atari_fb_predefined ; i++) {
+ for (i = 0 ; i < num_atafb_predefined ; i++) {
name=*(name_list++);
if (! name || ! *name)
break;
@@ -512,7 +470,7 @@ get_video_mode(char *vname)
#ifdef ATAFB_TT
static int tt_encode_fix( struct fb_fix_screeninfo *fix,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int mode;
@@ -539,7 +497,7 @@ static int tt_encode_fix( struct fb_fix_screeninfo *fix,
static int tt_decode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int xres=var->xres;
int yres=var->yres;
@@ -620,7 +578,7 @@ static int tt_decode_var( struct fb_var_screeninfo *var,
}
static int tt_encode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int linelen, i;
var->red.offset=0;
@@ -716,7 +674,7 @@ static int tt_encode_var( struct fb_var_screeninfo *var,
}
-static void tt_get_par( struct atari_fb_par *par )
+static void tt_get_par( struct atafb_par *par )
{
unsigned long addr;
par->hw.tt.mode=shifter_tt.tt_shiftmode;
@@ -727,7 +685,7 @@ static void tt_get_par( struct atari_fb_par *par )
par->screen_base = PTOV(addr);
}
-static void tt_set_par( struct atari_fb_par *par )
+static void tt_set_par( struct atafb_par *par )
{
shifter_tt.tt_shiftmode=par->hw.tt.mode;
shifter.syncmode=par->hw.tt.sync;
@@ -739,7 +697,7 @@ static void tt_set_par( struct atari_fb_par *par )
static int tt_getcolreg( unsigned regno, unsigned *red,
unsigned *green, unsigned *blue,
- unsigned *transp )
+ unsigned *transp, struct fb_info *info )
{
if ((shifter_tt.tt_shiftmode & TT_SHIFTER_MODEMASK) == TT_SHIFTER_STHIGH)
regno += 254;
@@ -756,7 +714,7 @@ static int tt_getcolreg( unsigned regno, unsigned *red,
static int tt_setcolreg( unsigned regno, unsigned red,
unsigned green, unsigned blue,
- unsigned transp )
+ unsigned transp, struct fb_info *info )
{
if ((shifter_tt.tt_shiftmode & TT_SHIFTER_MODEMASK) == TT_SHIFTER_STHIGH)
regno += 254;
@@ -772,7 +730,7 @@ static int tt_setcolreg( unsigned regno, unsigned red,
static int tt_detect( void )
-{ struct atari_fb_par par;
+{ struct atafb_par par;
/* Determine the connected monitor: The DMA sound must be
* disabled before reading the MFP GPIP, because the Sound
@@ -789,7 +747,7 @@ static int tt_detect( void )
mono_moni = (mfp.par_dt_reg & 0x80) == 0;
tt_get_par(&par);
- tt_encode_var(&atari_fb_predefined[0], &par);
+ tt_encode_var(&atafb_predefined[0], &par);
return 1;
}
@@ -807,10 +765,6 @@ static int f030_bus_width; /* Falcon ram bus width (for vid_control) */
#define F_MON_VGA 2
#define F_MON_TV 3
-/* Multisync monitor capabilities */
-/* Atari-TOS defaults if no boot option present */
-static long vfmin=58, vfmax=62, hfmin=31000, hfmax=32000;
-
static struct pixel_clock {
unsigned long f; /* f/[Hz] */
unsigned long t; /* t/[ps] (=1/f) */
@@ -837,7 +791,7 @@ static inline int hxx_prescale(struct falcon_hw *hw)
}
static int falcon_encode_fix( struct fb_fix_screeninfo *fix,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
strcpy(fix->id, "Atari Builtin");
fix->smem_start = (char *)real_screen_base;
@@ -867,7 +821,7 @@ static int falcon_encode_fix( struct fb_fix_screeninfo *fix,
static int falcon_decode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int bpp = var->bits_per_pixel;
int xres = var->xres;
@@ -943,7 +897,7 @@ static int falcon_decode_var( struct fb_var_screeninfo *var,
if (mon_type == F_MON_SM || DontCalcRes) {
/* Skip all calculations. VGA/TV/SC1224 only supported. */
- struct fb_var_screeninfo *myvar = &atari_fb_predefined[0];
+ struct fb_var_screeninfo *myvar = &atafb_predefined[0];
if (bpp > myvar->bits_per_pixel ||
var->xres > myvar->xres ||
@@ -1069,11 +1023,14 @@ static int falcon_decode_var( struct fb_var_screeninfo *var,
/* Choose master pixelclock depending on hor. timing */
plen = 1 * xstretch;
- if ((plen * xres + f25.right+f25.hsync+f25.left) * hfmin < f25.f)
+ if ((plen * xres + f25.right+f25.hsync+f25.left) *
+ fb_info.monspecs.hfmin < f25.f)
pclock = &f25;
- else if ((plen * xres + f32.right+f32.hsync+f32.left) * hfmin < f32.f)
+ else if ((plen * xres + f32.right+f32.hsync+f32.left) *
+ fb_info.monspecs.hfmin < f32.f)
pclock = &f32;
- else if ((plen * xres + fext.right+fext.hsync+fext.left) * hfmin < fext.f
+ else if ((plen * xres + fext.right+fext.hsync+fext.left) *
+ fb_info.monspecs.hfmin < fext.f
&& fext.f)
pclock = &fext;
else
@@ -1246,14 +1203,14 @@ static int falcon_decode_var( struct fb_var_screeninfo *var,
/* check hor. frequency */
hfreq = pclock->f / ((par->HHT+2)*prescale*2);
- if (hfreq > hfmax && mon_type!=F_MON_VGA) {
+ if (hfreq > fb_info.monspecs.hfmax && mon_type!=F_MON_VGA) {
/* ++guenther: ^^^^^^^^^^^^^^^^^^^ can't remember why I did this */
/* Too high -> enlarge margin */
left_margin += 1;
right_margin += 1;
goto again;
}
- if (hfreq > hfmax || hfreq < hfmin)
+ if (hfreq > fb_info.monspecs.hfmax || hfreq < fb_info.monspecs.hfmin)
return -EINVAL;
/* Vxx-registers */
@@ -1282,45 +1239,52 @@ static int falcon_decode_var( struct fb_var_screeninfo *var,
/* V-frequency check, hope I didn't create any loop here. */
/* Interlace and doubleline are mutually exclusive. */
vfreq = (hfreq * 2) / (par->VFT + 1);
- if (vfreq > vfmax && !doubleline && !interlace) {
+ if (vfreq > fb_info.monspecs.vfmax && !doubleline && !interlace) {
/* Too high -> try again with doubleline */
doubleline = 1;
goto again;
}
- else if (vfreq < vfmin && !interlace && !doubleline) {
+ else if (vfreq < fb_info.monspecs.vfmin && !interlace && !doubleline) {
/* Too low -> try again with interlace */
interlace = 1;
goto again;
}
- else if (vfreq < vfmin && doubleline) {
+ else if (vfreq < fb_info.monspecs.vfmin && doubleline) {
/* Doubleline too low -> clear doubleline and enlarge margins */
int lines;
doubleline = 0;
- for (lines=0; (hfreq*2)/(par->VFT+1+4*lines-2*yres)>vfmax; lines++)
+ for (lines=0;
+ (hfreq*2)/(par->VFT+1+4*lines-2*yres)>fb_info.monspecs.vfmax;
+ lines++)
;
upper_margin += lines;
lower_margin += lines;
goto again;
}
- else if (vfreq > vfmax && doubleline) {
+ else if (vfreq > fb_info.monspecs.vfmax && doubleline) {
/* Doubleline too high -> enlarge margins */
int lines;
- for (lines=0; (hfreq*2)/(par->VFT+1+4*lines)>vfmax; lines+=2)
+ for (lines=0;
+ (hfreq*2)/(par->VFT+1+4*lines)>fb_info.monspecs.vfmax;
+ lines+=2)
;
upper_margin += lines;
lower_margin += lines;
goto again;
}
- else if (vfreq > vfmax && interlace) {
+ else if (vfreq > fb_info.monspecs.vfmax && interlace) {
/* Interlace, too high -> enlarge margins */
int lines;
- for (lines=0; (hfreq*2)/(par->VFT+1+4*lines)>vfmax; lines++)
+ for (lines=0;
+ (hfreq*2)/(par->VFT+1+4*lines)>fb_info.monspecs.vfmax;
+ lines++)
;
upper_margin += lines;
lower_margin += lines;
goto again;
}
- else if (vfreq < vfmin || vfreq > vfmax)
+ else if (vfreq < fb_info.monspecs.vfmin ||
+ vfreq > fb_info.monspecs.vfmax)
return -EINVAL;
set_screen_base:
@@ -1339,7 +1303,7 @@ static int falcon_decode_var( struct fb_var_screeninfo *var,
}
static int falcon_encode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
/* !!! only for VGA !!! */
int linelen, i;
@@ -1425,12 +1389,13 @@ static int falcon_encode_var( struct fb_var_screeninfo *var,
var->transp.msb_right=0;
linelen = var->xres_virtual * var->bits_per_pixel / 8;
- if (screen_len)
+ if (screen_len) {
if (par->yres_virtual)
var->yres_virtual = par->yres_virtual;
else
/* yres_virtual==0 means use maximum */
var->yres_virtual = screen_len / linelen;
+ }
else {
if (hwscroll < 0)
var->yres_virtual = 2 * var->yres;
@@ -1506,7 +1471,7 @@ static int f_change_mode = 0;
static struct falcon_hw f_new_mode;
static int f_pan_display = 0;
-static void falcon_get_par( struct atari_fb_par *par )
+static void falcon_get_par( struct atafb_par *par )
{
unsigned long addr;
struct falcon_hw *hw = &par->hw.falcon;
@@ -1543,7 +1508,7 @@ static void falcon_get_par( struct atari_fb_par *par )
((hw->f_shift & 0x510)==0 && hw->st_shift==0x200);
}
-static void falcon_set_par( struct atari_fb_par *par )
+static void falcon_set_par( struct atafb_par *par )
{
f_change_mode = 0;
@@ -1627,7 +1592,7 @@ static void falcon_vbl_switcher( int irq, void *dummy, struct pt_regs *fp )
static int falcon_pan_display( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int xoffset;
int bpp = fb_display[currcon].var.bits_per_pixel;
@@ -1659,7 +1624,7 @@ static int falcon_pan_display( struct fb_var_screeninfo *var,
static int falcon_getcolreg( unsigned regno, unsigned *red,
unsigned *green, unsigned *blue,
- unsigned *transp )
+ unsigned *transp, struct fb_info *info )
{ unsigned long col;
if (regno > 255)
@@ -1679,7 +1644,7 @@ static int falcon_getcolreg( unsigned regno, unsigned *red,
static int falcon_setcolreg( unsigned regno, unsigned red,
unsigned green, unsigned blue,
- unsigned transp )
+ unsigned transp, struct fb_info *info )
{
if (regno > 255)
return 1;
@@ -1690,7 +1655,7 @@ static int falcon_setcolreg( unsigned regno, unsigned red,
(((green & 0xe) >> 1) | ((green & 1) << 3) << 4) |
((blue & 0xe) >> 1) | ((blue & 1) << 3);
#ifdef CONFIG_FBCON_CFB16
- packed16_cmap[regno] = (red << 11) | (green << 5) | blue;
+ fbcon_cfb16_cmap[regno] = (red << 11) | (green << 5) | blue;
#endif
}
return 0;
@@ -1738,7 +1703,7 @@ static int falcon_blank( int blank_mode )
static int falcon_detect( void )
{
- struct atari_fb_par par;
+ struct atafb_par par;
unsigned char fhw;
/* Determine connected monitor and set monitor parameters */
@@ -1748,18 +1713,18 @@ static int falcon_detect( void )
f030_bus_width = fhw << 6 & 0x80;
switch (mon_type) {
case F_MON_SM:
- vfmin = 70;
- vfmax = 72;
- hfmin = 35713;
- hfmax = 35715;
+ fb_info.monspecs.vfmin = 70;
+ fb_info.monspecs.vfmax = 72;
+ fb_info.monspecs.hfmin = 35713;
+ fb_info.monspecs.hfmax = 35715;
break;
case F_MON_SC:
case F_MON_TV:
/* PAL...NTSC */
- vfmin = 49; /* not 50, since TOS defaults to 49.9x Hz */
- vfmax = 60;
- hfmin = 15620;
- hfmax = 15755;
+ fb_info.monspecs.vfmin = 49; /* not 50, since TOS defaults to 49.9x Hz */
+ fb_info.monspecs.vfmax = 60;
+ fb_info.monspecs.hfmin = 15620;
+ fb_info.monspecs.hfmax = 15755;
break;
}
/* initialize hsync-len */
@@ -1769,7 +1734,7 @@ static int falcon_detect( void )
fext.hsync = h_syncs[mon_type] / fext.t;
falcon_get_par(&par);
- falcon_encode_var(&atari_fb_predefined[0], &par);
+ falcon_encode_var(&atafb_predefined[0], &par);
/* Detected mode is always the "autodetect" slot */
return 1;
@@ -1782,7 +1747,7 @@ static int falcon_detect( void )
#ifdef ATAFB_STE
static int stste_encode_fix( struct fb_fix_screeninfo *fix,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int mode;
@@ -1813,7 +1778,7 @@ static int stste_encode_fix( struct fb_fix_screeninfo *fix,
static int stste_decode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int xres=var->xres;
int yres=var->yres;
@@ -1871,7 +1836,7 @@ static int stste_decode_var( struct fb_var_screeninfo *var,
}
static int stste_encode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int linelen, i;
var->red.offset=0;
@@ -1922,12 +1887,13 @@ static int stste_encode_var( struct fb_var_screeninfo *var,
if (! use_hwscroll)
var->yres_virtual=var->yres;
- else if (screen_len)
+ else if (screen_len) {
if (par->yres_virtual)
var->yres_virtual = par->yres_virtual;
else
/* yres_virtual==0 means use maximum */
var->yres_virtual = screen_len / linelen;
+ }
else {
if (hwscroll < 0)
var->yres_virtual = 2 * var->yres;
@@ -1948,7 +1914,7 @@ static int stste_encode_var( struct fb_var_screeninfo *var,
}
-static void stste_get_par( struct atari_fb_par *par )
+static void stste_get_par( struct atafb_par *par )
{
unsigned long addr;
par->hw.st.mode=shifter_tt.st_shiftmode;
@@ -1960,7 +1926,7 @@ static void stste_get_par( struct atari_fb_par *par )
par->screen_base = PTOV(addr);
}
-static void stste_set_par( struct atari_fb_par *par )
+static void stste_set_par( struct atafb_par *par )
{
shifter_tt.st_shiftmode=par->hw.st.mode;
shifter.syncmode=par->hw.st.sync;
@@ -1972,7 +1938,7 @@ static void stste_set_par( struct atari_fb_par *par )
static int stste_getcolreg( unsigned regno, unsigned *red,
unsigned *green, unsigned *blue,
- unsigned *transp )
+ unsigned *transp, struct fb_info *info )
{ unsigned col;
if (regno > 15)
@@ -1995,7 +1961,7 @@ static int stste_getcolreg( unsigned regno, unsigned *red,
static int stste_setcolreg( unsigned regno, unsigned red,
unsigned green, unsigned blue,
- unsigned transp )
+ unsigned transp, struct fb_info *info )
{
if (regno > 15)
return 1;
@@ -2015,7 +1981,7 @@ static int stste_setcolreg( unsigned regno, unsigned red,
static int stste_detect( void )
-{ struct atari_fb_par par;
+{ struct atafb_par par;
/* Determine the connected monitor: The DMA sound must be
* disabled before reading the MFP GPIP, because the Sound
@@ -2028,7 +1994,7 @@ static int stste_detect( void )
mono_moni = (mfp.par_dt_reg & 0x80) == 0;
stste_get_par(&par);
- stste_encode_var(&atari_fb_predefined[0], &par);
+ stste_encode_var(&atafb_predefined[0], &par);
if (!ATARIHW_PRESENT(EXTD_SHIFTER))
use_hwscroll = 0;
@@ -2067,12 +2033,12 @@ static void stste_set_screen_base(unsigned long s_base)
#define SYNC_DELAY (mono_moni ? 1500 : 2000)
/* SWITCH_ACIA may be used for Falcon (ScreenBlaster III internal!) */
-static void st_ovsc_switch(int switchmode)
+static void st_ovsc_switch(void)
{
unsigned long flags;
register unsigned char old, new;
- if ((switchmode & (SWITCH_ACIA | SWITCH_SND6 | SWITCH_SND7)) == 0)
+ if (!(atari_switches & ATARI_SWITCH_OVSC_MASK))
return;
save_flags(flags);
cli();
@@ -2093,11 +2059,15 @@ static void st_ovsc_switch(int switchmode)
mfp.tim_ct_b = 0x10;
udelay(SYNC_DELAY);
- if (switchmode == SWITCH_ACIA)
- acia.key_ctrl = (ACIA_DIV64|ACIA_D8N1S|ACIA_RHTID|ACIA_RIE);
- else {
+ if (atari_switches & ATARI_SWITCH_OVSC_IKBD)
+ acia.key_ctrl = ACIA_DIV64 | ACIA_D8N1S | ACIA_RHTID | ACIA_RIE;
+ if (atari_switches & ATARI_SWITCH_OVSC_MIDI)
+ acia.mid_ctrl = ACIA_DIV16 | ACIA_D8N1S | ACIA_RHTID;
+ if (atari_switches & (ATARI_SWITCH_OVSC_SND6|ATARI_SWITCH_OVSC_SND7)) {
sound_ym.rd_data_reg_sel = 14;
- sound_ym.wd_data = sound_ym.rd_data_reg_sel | switchmode;
+ sound_ym.wd_data = sound_ym.rd_data_reg_sel |
+ ((atari_switches&ATARI_SWITCH_OVSC_SND6) ? 0x40:0) |
+ ((atari_switches&ATARI_SWITCH_OVSC_SND7) ? 0x80:0);
}
restore_flags(flags);
}
@@ -2107,7 +2077,7 @@ static void st_ovsc_switch(int switchmode)
#ifdef ATAFB_EXT
static int ext_encode_fix( struct fb_fix_screeninfo *fix,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
strcpy(fix->id,"Unknown Extern");
@@ -2157,9 +2127,9 @@ static int ext_encode_fix( struct fb_fix_screeninfo *fix,
static int ext_decode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
- struct fb_var_screeninfo *myvar = &atari_fb_predefined[0];
+ struct fb_var_screeninfo *myvar = &atafb_predefined[0];
if (var->bits_per_pixel > myvar->bits_per_pixel ||
var->xres > myvar->xres ||
@@ -2173,7 +2143,7 @@ static int ext_decode_var( struct fb_var_screeninfo *var,
static int ext_encode_var( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
int i;
@@ -2217,12 +2187,12 @@ static int ext_encode_var( struct fb_var_screeninfo *var,
}
-static void ext_get_par( struct atari_fb_par *par )
+static void ext_get_par( struct atafb_par *par )
{
par->screen_base = external_addr;
}
-static void ext_set_par( struct atari_fb_par *par )
+static void ext_set_par( struct atafb_par *par )
{
}
@@ -2238,10 +2208,8 @@ static void ext_set_par( struct atari_fb_par *par )
static int ext_getcolreg( unsigned regno, unsigned *red,
unsigned *green, unsigned *blue,
- unsigned *transp )
-
-{ unsigned char colmask = (1 << external_bitspercol) - 1;
-
+ unsigned *transp, struct fb_info *info )
+{
if (! external_vgaiobase)
return 1;
@@ -2254,7 +2222,7 @@ static int ext_getcolreg( unsigned regno, unsigned *red,
static int ext_setcolreg( unsigned regno, unsigned red,
unsigned green, unsigned blue,
- unsigned transp )
+ unsigned transp, struct fb_info *info )
{ unsigned char colmask = (1 << external_bitspercol) - 1;
@@ -2292,8 +2260,8 @@ static int ext_setcolreg( unsigned regno, unsigned red,
static int ext_detect( void )
{
- struct fb_var_screeninfo *myvar = &atari_fb_predefined[0];
- struct atari_fb_par dummy_par;
+ struct fb_var_screeninfo *myvar = &atafb_predefined[0];
+ struct atafb_par dummy_par;
myvar->xres = external_xres;
myvar->xres_virtual = external_xres_virtual;
@@ -2319,7 +2287,7 @@ static void set_screen_base(unsigned long s_base)
static int pan_display( struct fb_var_screeninfo *var,
- struct atari_fb_par *par )
+ struct atafb_par *par )
{
if (!fbhw->set_screen_base ||
(!ATARIHW_PRESENT(EXTD_SHIFTER) && var->xoffset))
@@ -2369,7 +2337,7 @@ static struct fb_hwswitch ext_switch = {
-static void atari_fb_get_par( struct atari_fb_par *par )
+static void atafb_get_par( struct atafb_par *par )
{
if (current_par_valid) {
*par=current_par;
@@ -2379,7 +2347,7 @@ static void atari_fb_get_par( struct atari_fb_par *par )
}
-static void atari_fb_set_par( struct atari_fb_par *par )
+static void atafb_set_par( struct atafb_par *par )
{
fbhw->set_par(par);
current_par=*par;
@@ -2396,7 +2364,7 @@ static void atari_fb_set_par( struct atari_fb_par *par )
/* used for hardware scrolling */
static int
-fb_update_var(int con)
+fb_update_var(int con, struct fb_info *info)
{
int off=fb_display[con].var.yoffset*fb_display[con].var.xres_virtual*
fb_display[con].var.bits_per_pixel>>3;
@@ -2412,12 +2380,12 @@ static int
do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
{
int err,activate;
- struct atari_fb_par par;
+ struct atafb_par par;
if ((err=fbhw->decode_var(var, &par)))
return err;
activate=var->activate;
if (((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) && isactive)
- atari_fb_set_par(&par);
+ atafb_set_par(&par);
fbhw->encode_var(var, &par);
var->activate=activate;
return 0;
@@ -2426,17 +2394,17 @@ do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
/* Functions for handling colormap */
static void
-do_install_cmap(int con)
+do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &(fb_display[con].var), 1,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
&(fb_display[con].var), 1,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
}
@@ -2444,7 +2412,7 @@ do_install_cmap(int con)
* Open/Release the frame buffer device
*/
-static int atari_fb_open(int fbidx)
+static int atafb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -2454,7 +2422,7 @@ static int atari_fb_open(int fbidx)
return(0);
}
-static int atari_fb_release(int fbidx)
+static int atafb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return(0);
@@ -2462,11 +2430,11 @@ static int atari_fb_release(int fbidx)
static int
-atari_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
+atafb_get_fix(struct fb_fix_screeninfo *fix, int con, struct fb_info *info)
{
- struct atari_fb_par par;
+ struct atafb_par par;
if (con == -1)
- atari_fb_get_par(&par);
+ atafb_get_par(&par);
else
fbhw->decode_var(&fb_display[con].var,&par);
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
@@ -2474,11 +2442,11 @@ atari_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
}
static int
-atari_fb_get_var(struct fb_var_screeninfo *var, int con)
+atafb_get_var(struct fb_var_screeninfo *var, int con, struct fb_info *info)
{
- struct atari_fb_par par;
+ struct atafb_par par;
if (con == -1) {
- atari_fb_get_par(&par);
+ atafb_get_par(&par);
fbhw->encode_var(var, &par);
}
else
@@ -2487,9 +2455,10 @@ atari_fb_get_var(struct fb_var_screeninfo *var, int con)
}
static void
-atari_fb_set_disp(int con)
+atafb_set_disp(int con, struct fb_info *info)
{
struct fb_fix_screeninfo fix;
+ struct fb_var_screeninfo var;
struct display *display;
if (con >= 0)
@@ -2497,7 +2466,8 @@ atari_fb_set_disp(int con)
else
display = &disp; /* used during initialization */
- atari_fb_get_fix(&fix, con);
+ atafb_get_fix(&fix, con, info);
+ atafb_get_var(&var, con, info);
if (con == -1)
con=0;
display->screen_base = (u_char *)fix.smem_start;
@@ -2514,10 +2484,50 @@ atari_fb_set_disp(int con)
display->can_soft_blank = 1;
display->inverse =
(fix.visual == FB_VISUAL_MONO01 ? !inverse : inverse);
+ switch (fix.type) {
+ case FB_TYPE_INTERLEAVED_PLANES:
+ switch (var.bits_per_pixel) {
+#ifdef CONFIG_FBCON_IPLAN2P2
+ case 2:
+ display->dispsw = &fbcon_iplan2p2;
+ break;
+#endif
+#ifdef CONFIG_FBCON_IPLAN2P4
+ case 4:
+ display->dispsw = &fbcon_iplan2p4;
+ break;
+#endif
+#ifdef CONFIG_FBCON_IPLAN2P8
+ case 8:
+ display->dispsw = &fbcon_iplan2p8;
+ break;
+#endif
+ }
+ break;
+ case FB_TYPE_PACKED_PIXELS:
+ switch (var.bits_per_pixel) {
+#ifdef CONFIG_FBCON_MFB
+ case 1:
+ display->dispsw = &fbcon_mfb;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_cfb8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ case 16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+#endif
+ }
+ break;
+ }
}
static int
-atari_fb_set_var(struct fb_var_screeninfo *var, int con)
+atafb_set_var(struct fb_var_screeninfo *var, int con, struct fb_info *info)
{
int err,oldxres,oldyres,oldbpp,oldxres_virtual,
oldyres_virtual,oldyoffset;
@@ -2536,10 +2546,10 @@ atari_fb_set_var(struct fb_var_screeninfo *var, int con)
|| oldyres_virtual != var->yres_virtual
|| oldbpp != var->bits_per_pixel
|| oldyoffset != var->yoffset) {
- atari_fb_set_disp(con);
+ atafb_set_disp(con, info);
(*fb_info.changevar)(con);
fb_alloc_cmap(&fb_display[con].cmap, 0, 0);
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
}
var->activate=0;
@@ -2549,22 +2559,22 @@ atari_fb_set_var(struct fb_var_screeninfo *var, int con)
static int
-atari_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+atafb_get_cmap(struct fb_cmap *cmap, int kspc, int con, struct fb_info *info)
{
if (con == currcon) /* current console ? */
return fb_get_cmap(cmap, &(fb_display[con].var), kspc,
- fbhw->getcolreg);
+ fbhw->getcolreg, info);
else
if (fb_display[con].cmap.len) /* non default colormap ? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return 0;
}
static int
-atari_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+atafb_set_cmap(struct fb_cmap *cmap, int kspc, int con, struct fb_info *info)
{
int err;
if (! fb_display[con].cmap.len) { /* no colormap allocated ? */
@@ -2575,14 +2585,14 @@ atari_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
}
if (con == currcon) /* current console ? */
return fb_set_cmap(cmap, &(fb_display[con].var), kspc,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
else
fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
return 0;
}
static int
-atari_fb_pan_display(struct fb_var_screeninfo *var, int con)
+atafb_pan_display(struct fb_var_screeninfo *var, int con, struct fb_info *info)
{
int xoffset = var->xoffset;
int yoffset = var->yoffset;
@@ -2606,33 +2616,33 @@ atari_fb_pan_display(struct fb_var_screeninfo *var, int con)
}
static int
-atari_fb_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
- unsigned long arg, int con)
+atafb_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
+ unsigned long arg, int con, struct fb_info *info)
{
switch (cmd) {
#ifdef FBCMD_GET_CURRENTPAR
case FBCMD_GET_CURRENTPAR:
if (copy_to_user((void *)arg, (void *)&current_par,
- sizeof(struct atari_fb_par)))
+ sizeof(struct atafb_par)))
return -EFAULT;
return 0;
#endif
#ifdef FBCMD_SET_CURRENTPAR
case FBCMD_SET_CURRENTPAR:
if (copy_from_user((void *)&current_par, (void *)arg,
- sizeof(struct atari_fb_par)))
+ sizeof(struct atafb_par)))
return -EFAULT;
- atari_fb_set_par(&current_par);
+ atafb_set_par(&current_par);
return 0;
#endif
}
return -EINVAL;
}
-static struct fb_ops atari_fb_ops = {
- atari_fb_open, atari_fb_release, atari_fb_get_fix, atari_fb_get_var,
- atari_fb_set_var, atari_fb_get_cmap, atari_fb_set_cmap,
- atari_fb_pan_display, atari_fb_ioctl
+static struct fb_ops atafb_ops = {
+ atafb_open, atafb_release, atafb_get_fix, atafb_get_var,
+ atafb_set_var, atafb_get_cmap, atafb_set_cmap,
+ atafb_pan_display, NULL, atafb_ioctl
};
static void
@@ -2645,14 +2655,14 @@ check_default_par( int detected_mode )
/* First try the user supplied mode */
if (default_par) {
- var=atari_fb_predefined[default_par-1];
+ var=atafb_predefined[default_par-1];
var.activate = FB_ACTIVATE_TEST;
if (do_fb_set_var(&var,1))
default_par=0; /* failed */
}
/* Next is the autodetected one */
if (! default_par) {
- var=atari_fb_predefined[detected_mode-1]; /* autodetect */
+ var=atafb_predefined[detected_mode-1]; /* autodetect */
var.activate = FB_ACTIVATE_TEST;
if (!do_fb_set_var(&var,1))
default_par=detected_mode;
@@ -2665,7 +2675,7 @@ check_default_par( int detected_mode )
default_par=get_video_mode(default_name);
if (! default_par)
panic("can't set default video mode\n");
- var=atari_fb_predefined[default_par-1];
+ var=atafb_predefined[default_par-1];
var.activate = FB_ACTIVATE_TEST;
if (! do_fb_set_var(&var,1))
break; /* ok */
@@ -2677,16 +2687,17 @@ check_default_par( int detected_mode )
}
static int
-atafb_switch(int con)
+atafb_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap ? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap,
- &(fb_display[currcon].var), 1, fbhw->getcolreg);
+ &(fb_display[currcon].var), 1, fbhw->getcolreg,
+ info);
do_fb_set_var(&fb_display[con].var,1);
currcon=con;
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return 0;
}
@@ -2698,7 +2709,7 @@ atafb_switch(int con)
* 4 = off
*/
static void
-atafb_blank(int blank)
+atafb_blank(int blank, struct fb_info *info)
{
unsigned short black[16];
struct fb_cmap cmap;
@@ -2713,19 +2724,13 @@ atafb_blank(int blank)
cmap.start=0;
cmap.len=16;
fb_set_cmap(&cmap, &(fb_display[currcon].var), 1,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
}
else
- do_install_cmap(currcon);
-}
-
-static int
-atafb_setcmap(struct fb_cmap *cmap, int con)
-{
- return(atari_fb_set_cmap(cmap, 1, con));
+ do_install_cmap(currcon, info);
}
-__initfunc(unsigned long atari_fb_init(unsigned long mem_start))
+__initfunc(unsigned long atafb_init(unsigned long mem_start))
{
int err;
int pad;
@@ -2770,6 +2775,16 @@ __initfunc(unsigned long atari_fb_init(unsigned long mem_start))
panic("Cannot initialize video hardware\n");
#endif
} while (0);
+
+ /* Multisync monitor capabilities */
+ /* Atari-TOS defaults if no boot option present */
+ if (fb_info.monspecs.hfmin == 0) {
+ fb_info.monspecs.hfmin = 31000;
+ fb_info.monspecs.hfmax = 32000;
+ fb_info.monspecs.vfmin = 58;
+ fb_info.monspecs.vfmax = 62;
+ }
+
detected_mode = fbhw->detect();
check_default_par(detected_mode);
#ifdef ATAFB_EXT
@@ -2778,13 +2793,14 @@ __initfunc(unsigned long atari_fb_init(unsigned long mem_start))
mem_req = default_mem_req + ovsc_offset +
ovsc_addlen;
mem_req = ((mem_req + PAGE_SIZE - 1) & PAGE_MASK) + PAGE_SIZE;
- screen_base = (unsigned long) atari_stram_alloc(mem_req, &mem_start);
+ screen_base = (unsigned long)atari_stram_alloc(mem_req, &mem_start,
+ "atafb");
memset((char *) screen_base, 0, mem_req);
pad = ((screen_base + PAGE_SIZE-1) & PAGE_MASK) - screen_base;
screen_base+=pad;
real_screen_base=screen_base+ovsc_offset;
screen_len = (mem_req - pad - ovsc_offset) & PAGE_MASK;
- st_ovsc_switch(ovsc_switchmode);
+ st_ovsc_switch();
if (CPU_IS_040_OR_060) {
/* On a '040+, the cache mode of video RAM must be set to
* write-through also for internal video hardware! */
@@ -2815,32 +2831,29 @@ __initfunc(unsigned long atari_fb_init(unsigned long mem_start))
strcpy(fb_info.modename, "Atari Builtin ");
fb_info.changevar = NULL;
fb_info.node = -1;
- fb_info.fbops = &atari_fb_ops;
- fb_info.fbvar_num = num_atari_fb_predefined;
- fb_info.fbvar = atari_fb_predefined;
+ fb_info.fbops = &atafb_ops;
fb_info.disp = &disp;
fb_info.switch_con = &atafb_switch;
fb_info.updatevar = &fb_update_var;
fb_info.blank = &atafb_blank;
- fb_info.setcmap = &atafb_setcmap;
- do_fb_set_var(&atari_fb_predefined[default_par-1], 1);
+ do_fb_set_var(&atafb_predefined[default_par-1], 1);
strcat(fb_info.modename, fb_var_names[default_par-1][0]);
err=register_framebuffer(&fb_info);
if (err < 0)
return(err);
- atari_fb_get_var(&disp.var, -1);
- atari_fb_set_disp(-1);
+ atafb_get_var(&disp.var, -1, &fb_info);
+ atafb_set_disp(-1, &fb_info);
printk("Determined %dx%d, depth %d\n",
disp.var.xres, disp.var.yres, disp.var.bits_per_pixel);
if ((disp.var.xres != disp.var.xres_virtual) ||
(disp.var.yres != disp.var.yres_virtual))
printk(" virtual %dx%d\n",
disp.var.xres_virtual, disp.var.yres_virtual);
- do_install_cmap(0);
- printk("%s frame buffer device, using %dK of video memory\n",
- fb_info.modename, screen_len>>10);
+ do_install_cmap(0, &fb_info);
+ printk("fb%d: %s frame buffer device, using %dK of video memory\n",
+ GET_FB_IDX(fb_info.node), fb_info.modename, screen_len>>10);
/* TODO: This driver cannot be unloaded yet */
MOD_INC_USE_COUNT;
@@ -2870,7 +2883,7 @@ static char * strtoke(char * s,const char * ct)
return sbegin;
}
-__initfunc(void atari_video_setup( char *options, int *ints ))
+__initfunc(void atafb_setup( char *options, int *ints ))
{
char *this_opt;
int temp;
@@ -2902,15 +2915,6 @@ __initfunc(void atari_video_setup( char *options, int *ints ))
if (hwscroll > 200)
hwscroll = 200;
}
- else if (! strncmp(this_opt, "sw_",3)) {
- if (! strcmp(this_opt+3, "acia"))
- ovsc_switchmode = SWITCH_ACIA;
- else if (! strcmp(this_opt+3, "snd6"))
- ovsc_switchmode = SWITCH_SND6;
- else if (! strcmp(this_opt+3, "snd7"))
- ovsc_switchmode = SWITCH_SND7;
- else ovsc_switchmode = SWITCH_NONE;
- }
#ifdef ATAFB_EXT
else if (!strcmp(this_opt,"mv300")) {
external_bitspercol = 8;
@@ -2939,12 +2943,8 @@ __initfunc(void atari_video_setup( char *options, int *ints ))
if (*int_str) {
/* Format to config extended internal video hardware like OverScan:
- "<switch-type>,internal:<xres>;<yres>;<xres_max>;<yres_max>;<offset>"
+ "internal:<xres>;<yres>;<xres_max>;<yres_max>;<offset>"
Explanation:
- <switch-type> type to switch on higher resolution
- sw_acia : via keyboard ACIA
- sw_snd6 : via bit 6 of the soundchip port
- sw_snd7 : via bit 7 of the soundchip port
<xres>: x-resolution
<yres>: y-resolution
The following are only needed if you have an overscan which
@@ -2974,9 +2974,9 @@ __initfunc(void atari_video_setup( char *options, int *ints ))
if (ovsc_offset || (sttt_yres_virtual != st_yres))
use_hwscroll=0;
+ int_invalid:
+ ;
}
- else
- int_invalid: ovsc_switchmode = SWITCH_NONE;
#ifdef ATAFB_EXT
if (*ext_str) {
@@ -3103,10 +3103,10 @@ __initfunc(void atari_video_setup( char *options, int *ints ))
hmax = 1000 * simple_strtoul(p, NULL, 10);
if (hmax <= 0 || hmax <= hmin) goto cap_invalid;
- vfmin = vmin;
- vfmax = vmax;
- hfmin = hmin;
- hfmax = hmax;
+ fb_info.monspecs.vfmin = vmin;
+ fb_info.monspecs.vfmax = vmax;
+ fb_info.monspecs.hfmin = hmin;
+ fb_info.monspecs.hfmax = hmax;
cap_invalid:
;
}
@@ -3126,9 +3126,9 @@ __initfunc(void atari_video_setup( char *options, int *ints ))
depth = simple_strtoul(p, NULL, 10);
if ((temp=get_video_mode("user0"))) {
default_par=temp;
- atari_fb_predefined[default_par-1].xres = xres;
- atari_fb_predefined[default_par-1].yres = yres;
- atari_fb_predefined[default_par-1].bits_per_pixel = depth;
+ atafb_predefined[default_par-1].xres = xres;
+ atafb_predefined[default_par-1].yres = yres;
+ atafb_predefined[default_par-1].bits_per_pixel = depth;
}
user_invalid:
@@ -3139,7 +3139,7 @@ __initfunc(void atari_video_setup( char *options, int *ints ))
#ifdef MODULE
int init_module(void)
{
- return(atari_fb_init(NULL));
+ return(atafb_init(NULL));
}
void cleanup_module(void)
@@ -3147,6 +3147,7 @@ void cleanup_module(void)
/* Not reached because the usecount will never
be decremented to zero */
unregister_framebuffer(&fb_info);
- /* TODO: clean up ... */
+ /* atari_stram_free( screen_base ); */
+ /* TODO: further clean up ... */
}
#endif /* MODULE */
diff --git a/drivers/video/ati-gt.h b/drivers/video/ati-gt.h
new file mode 100644
index 000000000..32dc792b5
--- /dev/null
+++ b/drivers/video/ati-gt.h
@@ -0,0 +1,203 @@
+/* the usage for the following structs vary from the gx and vt:
+and sdram and sgram gt's
+ pll registers (sdram) 6,7,11;
+ crtc_h_sync_strt_wid[3];
+ dsp1[3] (sdram,sgram,unused)
+ dsp2[3] (offset regbase+24, depends on colour mode);
+ crtc_h_tot_disp,crtc_v_tot_disp,crtc_v_sync_strt_wid,unused;
+ pll registers (sgram) 7,11;
+*/
+
+/* Register values for 1280x1024, 75Hz mode (20). no 16/32 */
+static struct aty_regvals aty_gt_reg_init_20 = {
+ { 0x41, 0xf9, 0x04 },
+ { 0xe02a7, 0x1401a6, 0 },
+ { 0x260957, 0x2806d6, 0 },
+ { 0x10006b6, 0x20006b6, 0x30006b6 },
+
+ 0x9f00d2, 0x03ff0429, 0x30400, 0,
+ { 0xb5, 0x04 }
+};
+
+#if 0
+/* Register values for 1280x960, 75Hz mode (19) */
+static struct aty_regvals aty_gt_reg_init_19 = {
+};
+#endif
+
+/* Register values for 1152x870, 75Hz mode (18) */
+static struct aty_regvals aty_gt_reg_init_18 = {
+ { 0x41, 0xe6, 0x04 },
+ { 0x300295, 0x300194, 0x300593 },
+ { 0x260a1c, 0x380561, 0},
+ { 0x1000744, 0x2000744, 0x3000744 },
+
+ 0x8f00b5, 0x3650392, 0x230368, 0,
+ { 0xe6, 0x04 }
+};
+
+/* Register values for 1024x768, 75Hz mode (17), 32 bpp untested */
+static struct aty_regvals aty_gt_reg_init_17 = {
+ { 0x41, 0xb5, 0x04 },
+ { 0xc0283, 0xc0182, 0xc0581 },
+ { 0x36066d, 0x3806d6, 0},
+ { 0xa0049e, 0x100049e, 0x200049e },
+
+ 0x7f00a3, 0x2ff031f, 0x30300, 0,
+ { 0xb8, 0x04 }
+};
+
+#if 0
+/* Register values for x, Hz mode (16) */
+static struct aty_regvals aty_gt_reg_init_16 = {
+};
+#endif
+
+/* Register values for 1024x768, 70Hz mode (15) */
+static struct aty_regvals aty_gt_reg_init_15 = {
+ { 0x41, 0xad, 0x04 },
+ { 0x310284, 0x310183, 0x310582 },
+ { 0x0, 0x380727 },
+ { 0x0 },
+ 0x7f00a5, 0x2ff0325, 0x260302,
+};
+
+/* Register values for 1024x768, 60Hz mode (14) */
+static struct aty_regvals aty_gt_reg_init_14 = {
+ { 0x40, 0xe1, 0x14 },
+ { 0x310284, 0x310183, 0x310582 },
+ { 0x3607c0, 0x380840, 0x0 },
+ { 0xa80592, 0x1000592, 0x0 },
+
+ 0x7f00a7, 0x2ff0325, 0x260302, 0,
+ { 0xe1, 0x14 }
+};
+
+/* Register values for 832x624, 75Hz mode (13) */
+static struct aty_regvals aty_gt_reg_init_13 = {
+ { 0x40, 0xc6, 0x14 },
+ { 0x28026d, 0x28016c, 0x28056b },
+ { 0x3608cf, 0x380960, 0 },
+ { 0xb00655, 0x1000655, 0x2000655 },
+
+ 0x67008f, 0x26f029a, 0x230270, 0,
+ { 0xc6, 0x14 }
+};
+
+/* Register values for 800x600, 75Hz mode (12) */
+static struct aty_regvals aty_gt_reg_init_12 = {
+ { 0x42, 0xe4, 0x04 },
+ { 0xa0267, 0xa0166, 0x0a0565},
+ { 0x360a33, 0x48056d, 0},
+ { 0xc00755, 0x1000755, 0x02000755},
+
+ 0x630083, 0x2570270, 0x30258, 0,
+ { 0xe4, 0x4 }
+};
+
+/* Register values for 800x600, 72Hz mode (11) */
+static struct aty_regvals aty_gt_reg_init_11 = {
+ { 0x42, 0xe6, 0x04 },
+ { 0xf026c, 0xf016b, 0xf056a },
+ { 0x360a1d, 0x480561, 0},
+ { 0xc00745, 0x1000745, 0x2000745 },
+
+ 0x630081, 0x02570299, 0x6027c
+};
+
+/* Register values for 800x600, 60Hz mode (10) */
+static struct aty_regvals aty_gt_reg_init_10 = {
+ { 0x42, 0xb8, 0x04 },
+ { 0x10026a, 0x100169, 0x100568 },
+ { 0x460652, 0x4806ba, 0},
+ { 0x68048b, 0xa0048b, 0x100048b },
+
+ 0x630083, 0x02570273, 0x40258, 0,
+ { 0xb8, 0x4 }
+};
+
+/* Register values for 800x600, 56Hz mode (9) */
+static struct aty_regvals aty_gt_reg_init_9 = {
+ { 0x42, 0xf9, 0x14 },
+ { 0x90268, 0x90167, 0x090566 },
+ { 0x460701, 0x480774, 0},
+ { 0x700509, 0xa80509, 0x1000509 },
+
+ 0x63007f, 0x2570270, 0x20258
+};
+
+#if 0
+/* Register values for 768x576, 50Hz mode (8) */
+static struct aty_regvals aty_gt_reg_init_8 = {
+};
+
+/* Register values for 640x870, 75Hz Full Page Display (7) */
+static struct aty_regvals aty_gt_reg_init_7 = {
+};
+#endif
+
+/* Register values for 640x480, 67Hz mode (6) */
+static struct aty_regvals aty_gt_reg_init_6 = {
+ { 0x42, 0xd1, 0x14 },
+ { 0x280259, 0x280158, 0x280557 },
+ { 0x460858, 0x4808e2, 0},
+ { 0x780600, 0xb00600, 0x1000600 },
+
+ 0x4f006b, 0x1df020c, 0x2301e2, 0,
+ { 0x8b, 0x4 }
+};
+
+/* Register values for 640x480, 60Hz mode (5) */
+static struct aty_regvals aty_gt_reg_init_5 = {
+ { 0x43, 0xe8, 0x04 },
+ { 0x2c0253, 0x2c0152, 0x2c0551 },
+ { 0x460a06, 0x580555, 0},
+ { 0x880734, 0xc00734, 0x1000734 },
+
+ 0x4f0063, 0x1df020c, 0x2201e9, 0,
+ { 0xe8, 0x04 }
+};
+
+#if 0
+/* Register values for x, Hz mode (4) */
+static struct aty_regvals aty_gt_reg_init_4 = {
+};
+
+/* Register values for x, Hz mode (3) */
+static struct aty_regvals aty_gt_reg_init_3 = {
+};
+
+/* Register values for x, Hz mode (2) */
+static struct aty_regvals aty_gt_reg_init_2 = {
+};
+
+/* Register values for x, Hz mode (1) */
+static struct aty_regvals aty_gt_reg_init_1 = {
+};
+#endif
+
+/* yikes, more data structures (dsp2)
+ * XXX kludge for sgram
+ */
+static int sgram_dsp[20][3] = {
+ {0,0,0},
+ {0,0,0},
+ {0,0,0},
+ {0,0,0},
+ {0x5203d7,0x7803d9,0xb803dd}, //5
+ {0x940666,0xe0066a,0x1700672}, //6
+ {0,0,0},
+ {0,0,0},
+ {0x88055f,0xd80563,0x170056b}, //9
+ {0x8404d9,0xb804dd,0x17004e5}, //10
+ {0x7803e2,0xb803e6,0x17003ee}, //11
+ {0x7803eb,0xb803ef,0x17003f7}, //12
+ {0xe806c5,0x17006cd,0x2e006dd}, //13
+ {0xe005f6,0x17005fe,0x2e0060e}, //14
+ {0xd8052c,0x1700534,0x2e00544}, //15
+ {0,0,0},
+ {0xb804f2,0x17004e5,0x2e0050a}, //17
+ {0xb803e6,0x17003ee,0x2e003fe}, //18
+ {0,0,0},
+ {0,0,0},
+};
diff --git a/drivers/video/ati-gx.h b/drivers/video/ati-gx.h
new file mode 100644
index 000000000..df48c1865
--- /dev/null
+++ b/drivers/video/ati-gx.h
@@ -0,0 +1,122 @@
+/* Register values for 1280x1024, 75Hz (WAS 60) mode (20) */
+static struct aty_regvals aty_gx_reg_init_20 = {
+ { 0x200, 0x200, 0x200 },
+
+ { 0x1200a5, 0x1200a3, 0x1200a3 },
+ { 0x30c0200, 0x30e0300, 0x30e0300 },
+ { 0x2, 0x3, 0x3 },
+
+ 0x9f00d2, 0x3ff0429, 0x30400, 0x28100040,
+ { 0xd4, 0x9 }
+};
+
+/* Register values for 1152x870, 75Hz mode (18) */
+static struct aty_regvals aty_gx_reg_init_18 = {
+ { 0x200, 0x200, 0x200 },
+
+ { 0x300097, 0x300095, 0x300094 },
+ { 0x3090200, 0x30e0300, 0x30e0600 },
+ { 0x2, 0x3, 0x6 },
+
+ 0x8f00b5, 0x3650392, 0x230368, 0x24100040,
+ { 0x53, 0x3 }
+};
+
+/* Register values for 1024x768, 75Hz mode (17) */
+static struct aty_regvals aty_gx_reg_init_17 = {
+ { 0x200, 0x200, 0x200 },
+
+ { 0x2c0087, 0x2c0085, 0x2c0084 },
+ { 0x3070200, 0x30e0300, 0x30e0600 },
+ { 0x2, 0x3, 0x6 },
+
+ 0x7f00a5, 0x2ff0323, 0x230302, 0x20100000,
+ { 0x42, 0x3 }
+};
+
+/* Register values for 1024x768, 72Hz mode (15) */
+static struct aty_regvals aty_gx_reg_init_15 = {
+ { 0, 0, 0 },
+
+ { 0x310086, 0x310084, 0x310084 },
+ { 0x3070200, 0x30e0300, 0x30e0300 },
+ { 0x2002312, 0x3002312, 0x3002312 },
+
+ 0x7f00a5, 0x2ff0325, 0x260302, 0x20100000,
+ { 0x88, 0x7 }
+};
+
+/* Register values for 1024x768, 60Hz mode (14) */
+static struct aty_regvals aty_gx_reg_init_14 = {
+ { 0, 0, 0 },
+
+ { 0x310086, 0x310084, 0x310084 },
+ { 0x3060200, 0x30d0300, 0x30d0300 },
+ { 0x2002312, 0x3002312, 0x3002312 },
+
+ 0x7f00a7, 0x2ff0325, 0x260302, 0x20100000,
+ { 0x6c, 0x6 }
+};
+
+/* Register values for 832x624, 75Hz mode (13) */
+static struct aty_regvals aty_gx_reg_init_13 = {
+ { 0x200, 0x200, 0x200 },
+
+ { 0x28006f, 0x28006d, 0x28006c },
+ { 0x3050200, 0x30b0300, 0x30e0600 },
+ { 0x2, 0x3, 0x6 },
+
+ 0x67008f, 0x26f029a, 0x230270, 0x1a100040,
+ { 0x4f, 0x5 }
+};
+
+#if 0 /* not filled in yet */
+/* Register values for 800x600, 75Hz mode (12) */
+static struct aty_regvals aty_gx_reg_init_12 = {
+ { 0x10, 0x28, 0x50 },
+ { },
+ { } /* pixel clock = 49.11MHz for V=74.40Hz */
+};
+
+/* Register values for 800x600, 72Hz mode (11) */
+static struct aty_regvals aty_gx_reg_init_11 = {
+ { 0x10, 0x28, 0x50 },
+ { },
+ { } /* pixel clock = 49.63MHz for V=71.66Hz */
+};
+
+/* Register values for 800x600, 60Hz mode (10) */
+static struct aty_regvals aty_gx_reg_init_10 = {
+ { 0x10, 0x28, 0x50 },
+ { },
+ { } /* pixel clock = 41.41MHz for V=59.78Hz */
+};
+
+/* Register values for 640x870, 75Hz Full Page Display (7) */
+static struct aty_regvals aty_gx_reg_init_7 = {
+ { 0x10, 0x30, 0x68 },
+ { },
+ { } /* pixel clock = 57.29MHz for V=75.01Hz */
+};
+#endif
+
+/* Register values for 640x480, 67Hz mode (6) */
+static struct aty_regvals aty_gx_reg_init_6 = {
+ { 0x200, 0x200, 0x200 },
+
+ { 0x28005b, 0x280059, 0x280058 },
+ { 0x3040200, 0x3060300, 0x30c0600 },
+ { 0x2002312, 0x3002312, 0x6002312 },
+
+ 0x4f006b, 0x1df020c, 0x2301e2, 0x14100040,
+ { 0x35, 0x07 }
+};
+
+#if 0 /* not filled in yet */
+/* Register values for 640x480, 60Hz mode (5) */
+static struct aty_regvals aty_gx_reg_init_5 = {
+ { 0x200, 0x200, 0x200 },
+ { },
+ { 0x35, 0x07 }
+};
+#endif
diff --git a/drivers/video/ati-vt.h b/drivers/video/ati-vt.h
new file mode 100644
index 000000000..3b25d6d5d
--- /dev/null
+++ b/drivers/video/ati-vt.h
@@ -0,0 +1,147 @@
+/* Register values for 1280x1024, 60Hz mode (20) */
+static struct aty_regvals aty_vt_reg_init_20 = {
+ { 0, 0, 0 },
+
+ { 0x002e02a7, 0x002e02a7, 0 },
+ { 0x03070200, 0x03070200, 0 },
+ { 0x0a00cb22, 0x0b00cb23, 0 },
+
+ 0x009f00d2, 0x03ff0429, 0x00030400, 0x28000000,
+ { 0x00, 0xaa }
+};
+
+/* Register values for 1280x960, 75Hz mode (19) */
+static struct aty_regvals aty_vt_reg_init_19 = {
+ { 0, 0, 0 },
+ { 0x003202a3, 0x003201a2, 0 },
+ { 0x030b0200, 0x030b0300, 0 },
+ { 0x0a00cb22, 0x0b00cb23, 0 },
+
+ 0x009f00d1, 0x03bf03e7, 0x000303c0, 0x28000000,
+ { 0x00, 0xc6 }
+};
+
+/* Register values for 1152x870, 75Hz mode (18) */
+static struct aty_regvals aty_vt_reg_init_18 = {
+ { 0, 0, 0 },
+
+ { 0x00300295, 0x00300194, 0 },
+ { 0x03080200, 0x03080300, 0 },
+ { 0x0a00cb21, 0x0b00cb22, 0 },
+
+ 0x008f00b5, 0x03650392, 0x00230368, 0x24000000,
+ { 0x00, 0x9d }
+};
+
+/* Register values for 1024x768, 75Hz mode (17) */
+static struct aty_regvals aty_vt_reg_init_17 = {
+ { 0, 0, 0 },
+
+ { 0x002c0283, 0x002c0182, 0 },
+ { 0x03080200, 0x03080300, 0 },
+ { 0x0a00cb21, 0x0b00cb22, 0 },
+
+ 0x007f00a3, 0x02ff031f, 0x00030300, 0x20000000,
+ { 0x01, 0xf7 }
+};
+
+/* Register values for 1024x768, 70Hz mode (15) */
+static struct aty_regvals aty_vt_reg_init_15 = {
+ { 0, 0, 0 },
+ { 0x00310284, 0x00310183, 0 },
+ { 0x03080200, 0x03080300, 0 },
+ { 0x0a00cb21, 0x0b00cb22, 0 },
+
+ 0x007f00a5, 0x02ff0325, 0x00260302, 0x20000000,
+ { 0x01, 0xeb }
+};
+
+/* Register values for 1024x768, 60Hz mode (14) */
+static struct aty_regvals aty_vt_reg_init_14 = {
+ { 0, 0, 0 },
+
+ { 0x00310284, 0x00310183, 0x00310582 }, /* 32 bit 0x00310582 */
+ { 0x03080200, 0x03080300, 0x03070600 }, /* 32 bit 0x03070600 */
+ { 0x0a00cb21, 0x0b00cb22, 0x0e00cb23 },
+
+ 0x007f00a7, 0x02ff0325, 0x00260302, 0x20000000,
+ { 0x01, 0xcc }
+};
+
+/* Register values for 832x624, 75Hz mode (13) */
+static struct aty_regvals aty_vt_reg_init_13 = {
+ { 0, 0, 0 },
+
+ { 0x0028026d, 0x0028016c, 0x0028056b },
+ { 0x03080200, 0x03070300, 0x03090600 },
+ { 0x0a00cb21, 0x0b00cb21, 0x0e00cb22 },
+
+ 0x0067008f, 0x026f029a, 0x00230270, 0x1a000000,
+ { 0x01, 0xb4 }
+};
+
+/* Register values for 800x600, 75Hz mode (12) */
+static struct aty_regvals aty_vt_reg_init_12 = {
+ { 0, 0, 0 },
+
+ { 0x002a0267, 0x002a0166, 0x002a0565 },
+ { 0x03040200, 0x03060300, 0x03070600 },
+ { 0x0a00cb21, 0x0b00cb21, 0x0e00cb22 },
+
+ 0x00630083, 0x02570270, 0x00030258, 0x19000000,
+ { 0x01, 0x9c }
+};
+
+/* Register values for 800x600, 72Hz mode (11) */
+static struct aty_regvals aty_vt_reg_init_11 = {
+ { 0, 0, 0 },
+
+ { 0x002f026c, 0x002f016b, 0x002f056a },
+ { 0x03050200, 0x03070300, 0x03090600 },
+ { 0x0a00cb21, 0x0b00cb21, 0x0e00cb22 },
+
+ 0x00630081, 0x02570299, 0x0006027c, 0x19000000,
+ { 0x01, 0x9d }
+};
+
+/* Register values for 800x600, 60Hz mode (10) */
+static struct aty_regvals aty_vt_reg_init_10 = {
+ { 0, 0, 0 },
+
+ { 0x0030026a, 0x00300169, 0x00300568 },
+ { 0x03050200, 0x03070300, 0x03090600 },
+ { 0x0a00cb21, 0x0b00cb21, 0x0e00cb22 },
+
+ 0x00630083, 0x02570273, 0x00040258, 0x19000000,
+ { 0x02, 0xfb }
+};
+
+/* Register values for 640x480, 67Hz mode (6) */
+static struct aty_regvals aty_vt_reg_init_6 = {
+ { 0, 0, 0 },
+
+ { 0x00280259, 0x00280158, 0x00280557 },
+ { 0x03050200, 0x03070300, 0x030a0600 },
+ { 0x0a00cb21, 0x0b00cb21, 0x0e00cb22 },
+
+ 0x004f006b, 0x01df020c, 0x002301e2, 0x14000000,
+ { 0x02, 0xbe }
+};
+
+/* Register values for 640x480, 60Hz mode (5) */
+static struct aty_regvals aty_vt_reg_init_5 = {
+ { 0, 0, 0 },
+
+ { 0x002c0253, 0x002c0152, 0x002c0551 },
+ { 0x03050200, 0x03070300, 0x03090600 },
+ { 0x0a00cb21, 0x0b00cb21, 0x0e00cb22 },
+
+ 0x004f0063, 0x01df020c, 0x002201e9, 0x14000000,
+ { 0x02, 0x9e }
+};
+ /* 8 bit 15 bit 32 bit */
+static int vt_mem_cntl[3][3] = { { 0x0A00CB21, 0x0B00CB21, 0x0E00CB21 }, /* 1 MB VRAM */
+ { 0x0A00CB22, 0x0B00CB22, 0x0E00CB22 }, /* 2 MB VRAM */
+ { 0x0200053B, 0x0300053B, 0x0600053B } /* 4 M B VRAM */
+ };
+
diff --git a/drivers/video/aty.h b/drivers/video/aty.h
new file mode 100644
index 000000000..7c9b00ad7
--- /dev/null
+++ b/drivers/video/aty.h
@@ -0,0 +1,923 @@
+/*
+ * Exported procedures for the ATI/mach64 display driver on PowerMacs.
+ *
+ * Copyright (C) 1997 Michael AK Tesch
+ * written with much help from Jon Howell
+ *
+ * Updated for 3D RAGE PRO by Geert Uytterhoeven
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+/*
+ * most of the rest of this file comes from ATI sample code
+ */
+#ifndef REGMACH64_H
+#define REGMACH64_H
+
+/* NON-GUI MEMORY MAPPED Registers - expressed in BYTE offsets */
+
+#define CRTC_H_TOTAL_DISP 0x0000 /* Dword offset 0_00 */
+#define CRTC_H_SYNC_STRT_WID 0x0004 /* Dword offset 0_01 */
+#define CRTC_H_SYNC_STRT 0x0004
+#define CRTC_H_SYNC_DLY 0x0005
+#define CRTC_H_SYNC_WID 0x0006
+
+#define CRTC_V_TOTAL_DISP 0x0008 /* Dword offset 0_02 */
+#define CRTC_V_TOTAL 0x0008
+#define CRTC_V_DISP 0x000A
+#define CRTC_V_SYNC_STRT_WID 0x000C /* Dword offset 0_03 */
+#define CRTC_V_SYNC_STRT 0x000C
+#define CRTC_V_SYNC_WID 0x000E
+
+#define CRTC_VLINE_CRNT_VLINE 0x0010 /* Dword offset 0_04 */
+#define CRTC_OFF_PITCH 0x0014 /* Dword offset 0_05 */
+#define CRTC_OFFSET 0x0014
+#define CRTC_PITCH 0x0016
+
+#define CRTC_INT_CNTL 0x0018 /* Dword offset 0_06 */
+#define CRTC_GEN_CNTL 0x001C /* Dword offset 0_07 */
+#define CRTC_PIX_WIDTH 0x001D
+#define CRTC_FIFO 0x001E
+#define CRTC_EXT_DISP 0x001F
+
+#define DSP_CONFIG 0x0020 /* Dword offset 0_08 */
+#define DSP_ON_OFF 0x0024 /* Dword offset 0_09 */
+#define TIMER_CONFIG 0x0028 /* Dword offset 0_0A */
+#define MEM_BUF_CNTL 0x002C /* Dword offset 0_0B */
+#define MEM_ADDR_CONFIG 0x0034 /* Dword offset 0_0D */
+
+#define CRT_TRAP 0x0038 /* Dword offset 0_0E */
+
+#define I2C_CNTL_0 0x003C /* Dword offset 0_0F */
+
+#define OVR_CLR 0x0040 /* Dword offset 0_10 */
+#define OVR_WID_LEFT_RIGHT 0x0044 /* Dword offset 0_11 */
+#define OVR_WID_TOP_BOTTOM 0x0048 /* Dword offset 0_12 */
+
+#define VGA_DSP_CONFIG 0x004C /* Dword offset 0_13 */
+#define VGA_DSP_ON_OFF 0x0050 /* Dword offset 0_14 */
+
+#define CUR_CLR0 0x0060 /* Dword offset 0_18 */
+#define CUR_CLR1 0x0064 /* Dword offset 0_19 */
+#define CUR_OFFSET 0x0068 /* Dword offset 0_1A */
+#define CUR_HORZ_VERT_POSN 0x006C /* Dword offset 0_1B */
+#define CUR_HORZ_VERT_OFF 0x0070 /* Dword offset 0_1C */
+
+#define GP_IO 0x0078 /* Dword offset 0_1E */
+
+#define HW_DEBUG 0x007C /* Dword offset 0_1F */
+
+#define SCRATCH_REG0 0x0080 /* Dword offset 0_20 */
+#define SCRATCH_REG1 0x0084 /* Dword offset 0_21 */
+
+#define CLOCK_CNTL 0x0090 /* Dword offset 0_24 */
+#define CLOCK_SEL_CNTL 0x0090 /* Dword offset 0_24 */
+
+#define CONFIG_STAT1 0x0094 /* Dword offset 0_25 */
+#define CONFIG_STAT2 0x0098 /* Dword offset 0_26 */
+
+#define BUS_CNTL 0x00A0 /* Dword offset 0_28 */
+
+#define EXT_MEM_CNTL 0x00AC /* Dword offset 0_2B */
+#define MEM_CNTL 0x00B0 /* Dword offset 0_2C */
+
+#define MEM_VGA_WP_SEL 0x00B4 /* Dword offset 0_2D */
+#define MEM_VGA_RP_SEL 0x00B8 /* Dword offset 0_2E */
+
+#define DAC_REGS 0x00C0 /* Dword offset 0_30 */
+#define DAC_W_INDEX 0x00C0 /* Dword offset 0_30 */
+#define DAC_DATA 0x00C1 /* Dword offset 0_30 */
+#define DAC_MASK 0x00C2 /* Dword offset 0_30 */
+#define DAC_R_INDEX 0x00C3 /* Dword offset 0_30 */
+#define DAC_CNTL 0x00C4 /* Dword offset 0_31 */
+
+#define EXT_DAC_REGS 0x00C8 /* Dword offset 0_32 */
+
+#define GEN_TEST_CNTL 0x00D0 /* Dword offset 0_34 */
+
+#define CUSTOM_MACRO_CNTL 0x00D4 /* Dword offset 0_35 */
+
+#define CONFIG_CNTL 0x00DC /* Dword offset 0_37 (CT, ET, VT) */
+#define CONFIG_CHIP_ID 0x00E0 /* Dword offset 0_38 */
+#define CONFIG_STAT0 0x00E4 /* Dword offset 0_39 */
+#define CRC_SIG 0x00E8 /* Dword offset 0_3A */
+
+
+/* GUI MEMORY MAPPED Registers */
+
+#define DST_OFF_PITCH 0x0100 /* Dword offset 0_40 */
+#define DST_X 0x0104 /* Dword offset 0_41 */
+#define DST_Y 0x0108 /* Dword offset 0_42 */
+#define DST_Y_X 0x010C /* Dword offset 0_43 */
+#define DST_WIDTH 0x0110 /* Dword offset 0_44 */
+#define DST_HEIGHT 0x0114 /* Dword offset 0_45 */
+#define DST_HEIGHT_WIDTH 0x0118 /* Dword offset 0_46 */
+#define DST_X_WIDTH 0x011C /* Dword offset 0_47 */
+#define DST_BRES_LNTH 0x0120 /* Dword offset 0_48 */
+#define DST_BRES_ERR 0x0124 /* Dword offset 0_49 */
+#define DST_BRES_INC 0x0128 /* Dword offset 0_4A */
+#define DST_BRES_DEC 0x012C /* Dword offset 0_4B */
+#define DST_CNTL 0x0130 /* Dword offset 0_4C */
+#define DST_Y_X__ALIAS__ 0x0134 /* Dword offset 0_4D */
+#define TRAIL_BRES_ERR 0x0138 /* Dword offset 0_4E */
+#define TRAIL_BRES_INC 0x013C /* Dword offset 0_4F */
+#define TRAIL_BRES_DEC 0x0140 /* Dword offset 0_50 */
+#define LEAD_BRES_LNTH 0x0144 /* Dword offset 0_51 */
+#define Z_OFF_PITCH 0x0148 /* Dword offset 0_52 */
+#define Z_CNTL 0x014C /* Dword offset 0_53 */
+#define ALPHA_TST_CNTL 0x0150 /* Dword offset 0_54 */
+#define SECONDARY_STW_EXP 0x0158 /* Dword offset 0_56 */
+#define SECONDARY_S_X_INC 0x015C /* Dword offset 0_57 */
+#define SECONDARY_S_Y_INC 0x0160 /* Dword offset 0_58 */
+#define SECONDARY_S_START 0x0164 /* Dword offset 0_59 */
+#define SECONDARY_W_X_INC 0x0168 /* Dword offset 0_5A */
+#define SECONDARY_W_Y_INC 0x016C /* Dword offset 0_5B */
+#define SECONDARY_W_START 0x0170 /* Dword offset 0_5C */
+#define SECONDARY_T_X_INC 0x0174 /* Dword offset 0_5D */
+#define SECONDARY_T_Y_INC 0x0178 /* Dword offset 0_5E */
+#define SECONDARY_T_START 0x017C /* Dword offset 0_5F */
+
+#define SRC_OFF_PITCH 0x0180 /* Dword offset 0_60 */
+#define SRC_X 0x0184 /* Dword offset 0_61 */
+#define SRC_Y 0x0188 /* Dword offset 0_62 */
+#define SRC_Y_X 0x018C /* Dword offset 0_63 */
+#define SRC_WIDTH1 0x0190 /* Dword offset 0_64 */
+#define SRC_HEIGHT1 0x0194 /* Dword offset 0_65 */
+#define SRC_HEIGHT1_WIDTH1 0x0198 /* Dword offset 0_66 */
+#define SRC_X_START 0x019C /* Dword offset 0_67 */
+#define SRC_Y_START 0x01A0 /* Dword offset 0_68 */
+#define SRC_Y_X_START 0x01A4 /* Dword offset 0_69 */
+#define SRC_WIDTH2 0x01A8 /* Dword offset 0_6A */
+#define SRC_HEIGHT2 0x01AC /* Dword offset 0_6B */
+#define SRC_HEIGHT2_WIDTH2 0x01B0 /* Dword offset 0_6C */
+#define SRC_CNTL 0x01B4 /* Dword offset 0_6D */
+
+#define SCALE_OFF 0x01C0 /* Dword offset 0_70 */
+#define SECONDARY_SCALE_OFF 0x01C4 /* Dword offset 0_71 */
+
+#define TEX_0_OFF 0x01C0 /* Dword offset 0_70 */
+#define TEX_1_OFF 0x01C4 /* Dword offset 0_71 */
+#define TEX_2_OFF 0x01C8 /* Dword offset 0_72 */
+#define TEX_3_OFF 0x01CC /* Dword offset 0_73 */
+#define TEX_4_OFF 0x01D0 /* Dword offset 0_74 */
+#define TEX_5_OFF 0x01D4 /* Dword offset 0_75 */
+#define TEX_6_OFF 0x01D8 /* Dword offset 0_76 */
+#define TEX_7_OFF 0x01DC /* Dword offset 0_77 */
+
+#define SCALE_WIDTH 0x01DC /* Dword offset 0_77 */
+#define SCALE_HEIGHT 0x01E0 /* Dword offset 0_78 */
+
+#define TEX_8_OFF 0x01E0 /* Dword offset 0_78 */
+#define TEX_9_OFF 0x01E4 /* Dword offset 0_79 */
+#define TEX_10_OFF 0x01E8 /* Dword offset 0_7A */
+#define S_Y_INC 0x01EC /* Dword offset 0_7B */
+
+#define SCALE_PITCH 0x01EC /* Dword offset 0_7B */
+#define SCALE_X_INC 0x01F0 /* Dword offset 0_7C */
+
+#define RED_X_INC 0x01F0 /* Dword offset 0_7C */
+#define GREEN_X_INC 0x01F4 /* Dword offset 0_7D */
+
+#define SCALE_Y_INC 0x01F4 /* Dword offset 0_7D */
+#define SCALE_VACC 0x01F8 /* Dword offset 0_7E */
+#define SCALE_3D_CNTL 0x01FC /* Dword offset 0_7F */
+
+#define HOST_DATA0 0x0200 /* Dword offset 0_80 */
+#define HOST_DATA1 0x0204 /* Dword offset 0_81 */
+#define HOST_DATA2 0x0208 /* Dword offset 0_82 */
+#define HOST_DATA3 0x020C /* Dword offset 0_83 */
+#define HOST_DATA4 0x0210 /* Dword offset 0_84 */
+#define HOST_DATA5 0x0214 /* Dword offset 0_85 */
+#define HOST_DATA6 0x0218 /* Dword offset 0_86 */
+#define HOST_DATA7 0x021C /* Dword offset 0_87 */
+#define HOST_DATA8 0x0220 /* Dword offset 0_88 */
+#define HOST_DATA9 0x0224 /* Dword offset 0_89 */
+#define HOST_DATAA 0x0228 /* Dword offset 0_8A */
+#define HOST_DATAB 0x022C /* Dword offset 0_8B */
+#define HOST_DATAC 0x0230 /* Dword offset 0_8C */
+#define HOST_DATAD 0x0234 /* Dword offset 0_8D */
+#define HOST_DATAE 0x0238 /* Dword offset 0_8E */
+#define HOST_DATAF 0x023C /* Dword offset 0_8F */
+#define HOST_CNTL 0x0240 /* Dword offset 0_90 */
+
+#define BM_HOSTDATA 0x0244 /* Dword offset 0_91 */
+#define BM_ADDR 0x0248 /* Dword offset 0_92 */
+#define BM_DATA 0x0248 /* Dword offset 0_92 */
+#define BM_GUI_TABLE_CMD 0x024C /* Dword offset 0_93 */
+
+#define PAT_REG0 0x0280 /* Dword offset 0_A0 */
+#define PAT_REG1 0x0284 /* Dword offset 0_A1 */
+#define PAT_CNTL 0x0288 /* Dword offset 0_A2 */
+
+#define SC_LEFT 0x02A0 /* Dword offset 0_A8 */
+#define SC_RIGHT 0x02A4 /* Dword offset 0_A9 */
+#define SC_LEFT_RIGHT 0x02A8 /* Dword offset 0_AA */
+#define SC_TOP 0x02AC /* Dword offset 0_AB */
+#define SC_BOTTOM 0x02B0 /* Dword offset 0_AC */
+#define SC_TOP_BOTTOM 0x02B4 /* Dword offset 0_AD */
+
+#define DP_BKGD_CLR 0x02C0 /* Dword offset 0_B0 */
+#define DP_FOG_CLR 0x02C4 /* Dword offset 0_B1 */
+#define DP_FRGD_CLR 0x02C4 /* Dword offset 0_B1 */
+#define DP_WRITE_MSK 0x02C8 /* Dword offset 0_B2 */
+#define DP_CHAIN_MSK 0x02CC /* Dword offset 0_B3 */
+#define DP_PIX_WIDTH 0x02D0 /* Dword offset 0_B4 */
+#define DP_MIX 0x02D4 /* Dword offset 0_B5 */
+#define DP_SRC 0x02D8 /* Dword offset 0_B6 */
+#define DP_FRGD_CLR_MIX 0x02DC /* Dword offset 0_B7 */
+#define DP_FRGD_BLGD_CLR 0x02E0 /* Dword offset 0_B8 */
+
+#define DST_X_Y 0x02E8 /* Dword offset 0_BA */
+#define DST_WIDTH_HEIGHT 0x02EC /* Dword offset 0_BB */
+#define USR_DST_PICTH 0x02F0 /* Dword offset 0_BC */
+#define DP_SET_GUI_ENGINE2 0x02F8 /* Dword offset 0_BE */
+#define DP_SET_GUI_ENGINE 0x02FC /* Dword offset 0_BF */
+
+#define CLR_CMP_CLR 0x0300 /* Dword offset 0_C0 */
+#define CLR_CMP_MSK 0x0304 /* Dword offset 0_C1 */
+#define CLR_CMP_CNTL 0x0308 /* Dword offset 0_C2 */
+
+#define FIFO_STAT 0x0310 /* Dword offset 0_C4 */
+
+#define CONTEXT_MASK 0x0320 /* Dword offset 0_C8 */
+#define CONTEXT_LOAD_CNTL 0x032C /* Dword offset 0_CB */
+
+#define GUI_TRAJ_CNTL 0x0330 /* Dword offset 0_CC */
+#define GUI_STAT 0x0338 /* Dword offset 0_CE */
+
+#define TEX_PALETTE_INDEX 0x0340 /* Dword offset 0_D0 */
+#define STW_EXP 0x0344 /* Dword offset 0_D1 */
+#define LOG_MAX_INC 0x0348 /* Dword offset 0_D2 */
+#define S_X_INC 0x034C /* Dword offset 0_D3 */
+#define S_Y_INC__ALIAS__ 0x0350 /* Dword offset 0_D4 */
+
+#define SCALE_PITCH__ALIAS__ 0x0350 /* Dword offset 0_D4 */
+
+#define S_START 0x0354 /* Dword offset 0_D5 */
+#define W_X_INC 0x0358 /* Dword offset 0_D6 */
+#define W_Y_INC 0x035C /* Dword offset 0_D7 */
+#define W_START 0x0360 /* Dword offset 0_D8 */
+#define T_X_INC 0x0364 /* Dword offset 0_D9 */
+#define T_Y_INC 0x0368 /* Dword offset 0_DA */
+
+#define SECONDARY_SCALE_PITCH 0x0368 /* Dword offset 0_DA */
+
+#define T_START 0x036C /* Dword offset 0_DB */
+#define TEX_SIZE_PITCH 0x0370 /* Dword offset 0_DC */
+#define TEX_CNTL 0x0374 /* Dword offset 0_DD */
+#define SECONDARY_TEX_OFFSET 0x0378 /* Dword offset 0_DE */
+#define TEX_PALETTE 0x037C /* Dword offset 0_DF */
+
+#define SCALE_PITCH_BOTH 0x0380 /* Dword offset 0_E0 */
+#define SECONDARY_SCALE_OFF_ACC 0x0384 /* Dword offset 0_E1 */
+#define SCALE_OFF_ACC 0x0388 /* Dword offset 0_E2 */
+#define SCALE_DST_Y_X 0x038C /* Dword offset 0_E3 */
+
+#define COMPOSITE_SHADOW_ID 0x0398 /* Dword offset 0_E6 */
+
+#define SECONDARY_SCALE_X_INC 0x039C /* Dword offset 0_E7 */
+
+#define SPECULAR_RED_X_INC 0x039C /* Dword offset 0_E7 */
+#define SPECULAR_RED_Y_INC 0x03A0 /* Dword offset 0_E8 */
+#define SPECULAR_RED_START 0x03A4 /* Dword offset 0_E9 */
+
+#define SECONDARY_SCALE_HACC 0x03A4 /* Dword offset 0_E9 */
+
+#define SPECULAR_GREEN_X_INC 0x03A8 /* Dword offset 0_EA */
+#define SPECULAR_GREEN_Y_INC 0x03AC /* Dword offset 0_EB */
+#define SPECULAR_GREEN_START 0x03B0 /* Dword offset 0_EC */
+#define SPECULAR_BLUE_X_INC 0x03B4 /* Dword offset 0_ED */
+#define SPECULAR_BLUE_Y_INC 0x03B8 /* Dword offset 0_EE */
+#define SPECULAR_BLUE_START 0x03BC /* Dword offset 0_EF */
+
+#define SCALE_X_INC__ALIAS__ 0x03C0 /* Dword offset 0_F0 */
+
+#define RED_X_INC__ALIAS__ 0x03C0 /* Dword offset 0_F0 */
+#define RED_Y_INC 0x03C4 /* Dword offset 0_F1 */
+#define RED_START 0x03C8 /* Dword offset 0_F2 */
+
+#define SCALE_HACC 0x03C8 /* Dword offset 0_F2 */
+#define SCALE_Y_INC__ALIAS__ 0x03CC /* Dword offset 0_F3 */
+
+#define GREEN_X_INC__ALIAS__ 0x03CC /* Dword offset 0_F3 */
+#define GREEN_Y_INC 0x03D0 /* Dword offset 0_F4 */
+
+#define SECONDARY_SCALE_Y_INC 0x03D0 /* Dword offset 0_F4 */
+#define SECONDARY_SCALE_VACC 0x03D4 /* Dword offset 0_F5 */
+
+#define GREEN_START 0x03D4 /* Dword offset 0_F5 */
+#define BLUE_X_INC 0x03D8 /* Dword offset 0_F6 */
+#define BLUE_Y_INC 0x03DC /* Dword offset 0_F7 */
+#define BLUE_START 0x03E0 /* Dword offset 0_F8 */
+#define Z_X_INC 0x03E4 /* Dword offset 0_F9 */
+#define Z_Y_INC 0x03E8 /* Dword offset 0_FA */
+#define Z_START 0x03EC /* Dword offset 0_FB */
+#define ALPHA_X_INC 0x03F0 /* Dword offset 0_FC */
+#define FOG_X_INC 0x03F0 /* Dword offset 0_FC */
+#define ALPHA_Y_INC 0x03F4 /* Dword offset 0_FD */
+#define FOG_Y_INC 0x03F4 /* Dword offset 0_FD */
+#define ALPHA_START 0x03F8 /* Dword offset 0_FE */
+#define FOG_START 0x03F8 /* Dword offset 0_FE */
+
+#define OVERLAY_Y_X_START 0x0400 /* Dword offset 1_00 */
+#define OVERLAY_Y_X_END 0x0404 /* Dword offset 1_01 */
+#define OVERLAY_VIDEO_KEY_CLR 0x0408 /* Dword offset 1_02 */
+#define OVERLAY_VIDEO_KEY_MSK 0x040C /* Dword offset 1_03 */
+#define OVERLAY_GRAPHICS_KEY_CLR 0x0410 /* Dword offset 1_04 */
+#define OVERLAY_GRAPHICS_KEY_MSK 0x0414 /* Dword offset 1_05 */
+#define OVERLAY_KEY_CNTL 0x0418 /* Dword offset 1_06 */
+
+#define OVERLAY_SCALE_INC 0x0420 /* Dword offset 1_08 */
+#define OVERLAY_SCALE_CNTL 0x0424 /* Dword offset 1_09 */
+#define SCALER_HEIGHT_WIDTH 0x0428 /* Dword offset 1_0A */
+#define SCALER_TEST 0x042C /* Dword offset 1_0B */
+#define SCALER_BUF0_OFFSET 0x0434 /* Dword offset 1_0D */
+#define SCALER_BUF1_OFFSET 0x0438 /* Dword offset 1_0E */
+#define SCALE_BUF_PITCH 0x043C /* Dword offset 1_0F */
+
+#define CAPTURE_START_END 0x0440 /* Dword offset 1_10 */
+#define CAPTURE_X_WIDTH 0x0444 /* Dword offset 1_11 */
+#define VIDEO_FORMAT 0x0448 /* Dword offset 1_12 */
+#define VBI_START_END 0x044C /* Dword offset 1_13 */
+#define CAPTURE_CONFIG 0x0450 /* Dword offset 1_14 */
+#define TRIG_CNTL 0x0454 /* Dword offset 1_15 */
+
+#define OVERLAY_EXCLUSIVE_HORZ 0x0458 /* Dword offset 1_16 */
+#define OVERLAY_EXCLUSIVE_VERT 0x045C /* Dword offset 1_17 */
+
+#define VAL_WIDTH 0x0460 /* Dword offset 1_18 */
+#define CAPTURE_DEBUG 0x0464 /* Dword offset 1_19 */
+#define VIDEO_SYNC_TEST 0x0468 /* Dword offset 1_1A */
+
+#define SNAPSHOT_VH_COUNTS 0x0470 /* Dword offset 1_1C */
+#define SNAPSHOT_F_COUNT 0x0474 /* Dword offset 1_1D */
+#define N_VIF_COUNT 0x0478 /* Dword offset 1_1E */
+#define SNAPSHOT_VIF_COUNT 0x047C /* Dword offset 1_1F */
+
+#define CAPTURE_BUF0_OFFSET 0x0480 /* Dword offset 1_20 */
+#define CAPTURE_BUF1_OFFSET 0x0484 /* Dword offset 1_21 */
+#define CAPTURE_BUF_PITCH 0x0488 /* Dword offset 1_22 */
+
+#define MPP_CONFIG 0x04C0 /* Dword offset 1_30 */
+#define MPP_STROBE_SEQ 0x04C4 /* Dword offset 1_31 */
+#define MPP_ADDR 0x04C8 /* Dword offset 1_32 */
+#define MPP_DATA 0x04CC /* Dword offset 1_33 */
+#define TVO_CNTL 0x0500 /* Dword offset 1_40 */
+
+#define CRT_HORZ_VERT_LOAD 0x0544 /* Dword offset 1_51 */
+
+#define AGP_BASE 0x0548 /* Dword offset 1_52 */
+#define AGP_CNTL 0x054C /* Dword offset 1_53 */
+
+#define SCALER_COLOUR_CNTL 0x0550 /* Dword offset 1_54 */
+#define SCALER_H_COEFF0 0x0554 /* Dword offset 1_55 */
+#define SCALER_H_COEFF1 0x0558 /* Dword offset 1_56 */
+#define SCALER_H_COEFF2 0x055C /* Dword offset 1_57 */
+#define SCALER_H_COEFF3 0x0560 /* Dword offset 1_58 */
+#define SCALER_H_COEFF4 0x0564 /* Dword offset 1_59 */
+
+#define GUI_CNTL 0x0578 /* Dword offset 1_5E */
+
+#define BM_FRAME_BUF_OFFSET 0x0580 /* Dword offset 1_60 */
+#define BM_SYSTEM_MEM_ADDR 0x0584 /* Dword offset 1_61 */
+#define BM_COMMAND 0x0588 /* Dword offset 1_62 */
+#define BM_STATUS 0x058C /* Dword offset 1_63 */
+#define BM_GUI_TABLE 0x05B8 /* Dword offset 1_6E */
+#define BM_SYSTEM_TABLE 0x05BC /* Dword offset 1_6F */
+
+#define SCALER_BUF0_OFFSET_U 0x05D4 /* Dword offset 1_75 */
+#define SCALER_BUF0_OFFSET_V 0x05D8 /* Dword offset 1_76 */
+#define SCALER_BUF1_OFFSET_U 0x05DC /* Dword offset 1_77 */
+#define SCALER_BUF1_OFFSET_V 0x05E0 /* Dword offset 1_78 */
+
+#define VERTEX_1_S 0x0640 /* Dword offset 1_90 */
+#define VERTEX_1_T 0x0644 /* Dword offset 1_91 */
+#define VERTEX_1_W 0x0648 /* Dword offset 1_92 */
+#define VERTEX_1_SPEC_ARGB 0x064C /* Dword offset 1_93 */
+#define VERTEX_1_Z 0x0650 /* Dword offset 1_94 */
+#define VERTEX_1_ARGB 0x0654 /* Dword offset 1_95 */
+#define VERTEX_1_X_Y 0x0658 /* Dword offset 1_96 */
+#define ONE_OVER_AREA 0x065C /* Dword offset 1_97 */
+#define VERTEX_2_S 0x0660 /* Dword offset 1_98 */
+#define VERTEX_2_T 0x0664 /* Dword offset 1_99 */
+#define VERTEX_2_W 0x0668 /* Dword offset 1_9A */
+#define VERTEX_2_SPEC_ARGB 0x066C /* Dword offset 1_9B */
+#define VERTEX_2_Z 0x0670 /* Dword offset 1_9C */
+#define VERTEX_2_ARGB 0x0674 /* Dword offset 1_9D */
+#define VERTEX_2_X_Y 0x0678 /* Dword offset 1_9E */
+#define ONE_OVER_AREA 0x065C /* Dword offset 1_9F */
+#define VERTEX_3_S 0x0680 /* Dword offset 1_A0 */
+#define VERTEX_3_T 0x0684 /* Dword offset 1_A1 */
+#define VERTEX_3_W 0x0688 /* Dword offset 1_A2 */
+#define VERTEX_3_SPEC_ARGB 0x068C /* Dword offset 1_A3 */
+#define VERTEX_3_Z 0x0690 /* Dword offset 1_A4 */
+#define VERTEX_3_ARGB 0x0694 /* Dword offset 1_A5 */
+#define VERTEX_3_X_Y 0x0698 /* Dword offset 1_A6 */
+#define ONE_OVER_AREA 0x065C /* Dword offset 1_A7 */
+#define VERTEX_1_S 0x0640 /* Dword offset 1_AB */
+#define VERTEX_1_T 0x0644 /* Dword offset 1_AC */
+#define VERTEX_1_W 0x0648 /* Dword offset 1_AD */
+#define VERTEX_2_S 0x0660 /* Dword offset 1_AE */
+#define VERTEX_2_T 0x0664 /* Dword offset 1_AF */
+#define VERTEX_2_W 0x0668 /* Dword offset 1_B0 */
+#define VERTEX_3_SECONDARY_S 0x06C0 /* Dword offset 1_B0 */
+#define VERTEX_3_S 0x0680 /* Dword offset 1_B1 */
+#define VERTEX_3_SECONDARY_T 0x06C4 /* Dword offset 1_B1 */
+#define VERTEX_3_T 0x0684 /* Dword offset 1_B2 */
+#define VERTEX_3_SECONDARY_W 0x06C8 /* Dword offset 1_B2 */
+#define VERTEX_3_W 0x0688 /* Dword offset 1_B3 */
+#define VERTEX_1_SPEC_ARGB 0x064C /* Dword offset 1_B4 */
+#define VERTEX_2_SPEC_ARGB 0x066C /* Dword offset 1_B5 */
+#define VERTEX_3_SPEC_ARGB 0x068C /* Dword offset 1_B6 */
+#define VERTEX_1_Z 0x0650 /* Dword offset 1_B7 */
+#define VERTEX_2_Z 0x0670 /* Dword offset 1_B8 */
+#define VERTEX_3_Z 0x0690 /* Dword offset 1_B9 */
+#define VERTEX_1_ARGB 0x0654 /* Dword offset 1_BA */
+#define VERTEX_2_ARGB 0x0674 /* Dword offset 1_BB */
+#define VERTEX_3_ARGB 0x0694 /* Dword offset 1_BC */
+#define VERTEX_1_X_Y 0x0658 /* Dword offset 1_BD */
+#define VERTEX_2_X_Y 0x0678 /* Dword offset 1_BE */
+#define VERTEX_3_X_Y 0x0698 /* Dword offset 1_BF */
+#define ONE_OVER_AREA_UC 0x0700 /* Dword offset 1_C0 */
+#define SETUP_CNTL 0x0704 /* Dword offset 1_C1 */
+#define VERTEX_1_SECONDARY_S 0x0728 /* Dword offset 1_CA */
+#define VERTEX_1_SECONDARY_T 0x072C /* Dword offset 1_CB */
+#define VERTEX_1_SECONDARY_W 0x0730 /* Dword offset 1_CC */
+#define VERTEX_2_SECONDARY_S 0x0734 /* Dword offset 1_CD */
+#define VERTEX_2_SECONDARY_T 0x0738 /* Dword offset 1_CE */
+#define VERTEX_2_SECONDARY_W 0x073C /* Dword offset 1_CF */
+
+
+/* CRTC control values (mostly CRTC_GEN_CNTL) */
+
+#define CRTC_H_SYNC_NEG 0x00200000
+#define CRTC_V_SYNC_NEG 0x00200000
+
+#define CRTC_DBL_SCAN_EN 0x00000001
+#define CRTC_INTERLACE_EN 0x00000002
+#define CRTC_HSYNC_DIS 0x00000004
+#define CRTC_VSYNC_DIS 0x00000008
+#define CRTC_CSYNC_EN 0x00000010
+#define CRTC_PIX_BY_2_EN 0x00000020 /* unused on RAGE */
+#define CRTC_DISPLAY_DIS 0x00000040
+#define CRTC_VGA_XOVERSCAN 0x00000040
+
+#define CRTC_PIX_WIDTH_MASK 0x00000700
+#define CRTC_PIX_WIDTH_4BPP 0x00000100
+#define CRTC_PIX_WIDTH_8BPP 0x00000200
+#define CRTC_PIX_WIDTH_15BPP 0x00000300
+#define CRTC_PIX_WIDTH_16BPP 0x00000400
+#define CRTC_PIX_WIDTH_24BPP 0x00000500
+#define CRTC_PIX_WIDTH_32BPP 0x00000600
+
+#define CRTC_BYTE_PIX_ORDER 0x00000800
+#define CRTC_PIX_ORDER_MSN_LSN 0x00000000
+#define CRTC_PIX_ORDER_LSN_MSN 0x00000800
+
+#define CRTC_FIFO_LWM 0x000f0000
+
+#define VGA_128KAP_PAGING 0x00100000
+#define VFC_SYNC_TRISTATE 0x00200000
+#define CRTC_LOCK_REGS 0x00400000
+#define CRTC_SYNC_TRISTATE 0x00800000
+
+#define CRTC_EXT_DISP_EN 0x01000000
+#define CRTC_ENABLE 0x02000000
+#define CRTC_DISP_REQ_ENB 0x04000000
+#define VGA_ATI_LINEAR 0x08000000
+#define CRTC_VSYNC_FALL_EDGE 0x10000000
+#define VGA_TEXT_132 0x20000000
+#define VGA_XCRT_CNT_EN 0x40000000
+#define VGA_CUR_B_TEST 0x80000000
+
+#define CRTC_CRNT_VLINE 0x07f00000
+#define CRTC_VBLANK 0x00000001
+
+
+/* DAC control values */
+
+#define DAC_EXT_SEL_RS2 0x01
+#define DAC_EXT_SEL_RS3 0x02
+#define DAC_8BIT_EN 0x00000100
+#define DAC_PIX_DLY_MASK 0x00000600
+#define DAC_PIX_DLY_0NS 0x00000000
+#define DAC_PIX_DLY_2NS 0x00000200
+#define DAC_PIX_DLY_4NS 0x00000400
+#define DAC_BLANK_ADJ_MASK 0x00001800
+#define DAC_BLANK_ADJ_0 0x00000000
+#define DAC_BLANK_ADJ_1 0x00000800
+#define DAC_BLANK_ADJ_2 0x00001000
+
+
+/* Mix control values */
+
+#define MIX_NOT_DST 0x0000
+#define MIX_0 0x0001
+#define MIX_1 0x0002
+#define MIX_DST 0x0003
+#define MIX_NOT_SRC 0x0004
+#define MIX_XOR 0x0005
+#define MIX_XNOR 0x0006
+#define MIX_SRC 0x0007
+#define MIX_NAND 0x0008
+#define MIX_NOT_SRC_OR_DST 0x0009
+#define MIX_SRC_OR_NOT_DST 0x000a
+#define MIX_OR 0x000b
+#define MIX_AND 0x000c
+#define MIX_SRC_AND_NOT_DST 0x000d
+#define MIX_NOT_SRC_AND_DST 0x000e
+#define MIX_NOR 0x000f
+
+/* Maximum engine dimensions */
+#define ENGINE_MIN_X 0
+#define ENGINE_MIN_Y 0
+#define ENGINE_MAX_X 4095
+#define ENGINE_MAX_Y 16383
+
+/* Mach64 engine bit constants - these are typically ORed together */
+
+/* BUS_CNTL register constants */
+#define BUS_FIFO_ERR_ACK 0x00200000
+#define BUS_HOST_ERR_ACK 0x00800000
+
+/* GEN_TEST_CNTL register constants */
+#define GEN_OVR_OUTPUT_EN 0x20
+#define HWCURSOR_ENABLE 0x80
+#define GUI_ENGINE_ENABLE 0x100
+#define BLOCK_WRITE_ENABLE 0x200
+
+/* DSP_CONFIG register constants */
+#define DSP_XCLKS_PER_QW 0x00003fff
+#define DSP_LOOP_LATENCY 0x000f0000
+#define DSP_PRECISION 0x00700000
+
+/* DSP_ON_OFF register constants */
+#define DSP_OFF 0x000007ff
+#define DSP_ON 0x07ff0000
+
+/* CLOCK_CNTL register constants */
+#define CLOCK_SEL 0x0f
+#define CLOCK_DIV 0x30
+#define CLOCK_DIV1 0x00
+#define CLOCK_DIV2 0x10
+#define CLOCK_DIV4 0x20
+#define CLOCK_STROBE 0x40
+#define PLL_WR_EN 0x02
+
+/* PLL registers */
+#define PLL_MACRO_CNTL 0x01
+#define PLL_REF_DIV 0x02
+#define PLL_GEN_CNTL 0x03
+#define MCLK_FB_DIV 0x04
+#define PLL_VCLK_CNTL 0x05
+#define VCLK_POST_DIV 0x06
+#define VCLK0_FB_DIV 0x07
+#define VCLK1_FB_DIV 0x08
+#define VCLK2_FB_DIV 0x09
+#define VCLK3_FB_DIV 0x0A
+#define PLL_XCLK_CNTL 0x0B
+#define PLL_TEST_CTRL 0x0E
+#define PLL_TEST_COUNT 0x0F
+
+/* Fields in PLL registers */
+#define PLL_PC_GAIN 0x07
+#define PLL_VC_GAIN 0x18
+#define PLL_DUTY_CYC 0xE0
+#define PLL_OVERRIDE 0x01
+#define PLL_MCLK_RST 0x02
+#define OSC_EN 0x04
+#define EXT_CLK_EN 0x08
+#define MCLK_SRC_SEL 0x70
+#define EXT_CLK_CNTL 0x80
+#define VCLK_SRC_SEL 0x03
+#define PLL_VCLK_RST 0x04
+#define VCLK_INVERT 0x08
+#define VCLK0_POST 0x03
+#define VCLK1_POST 0x0C
+#define VCLK2_POST 0x30
+#define VCLK3_POST 0xC0
+
+/* CONFIG_CNTL register constants */
+#define APERTURE_4M_ENABLE 1
+#define APERTURE_8M_ENABLE 2
+#define VGA_APERTURE_ENABLE 4
+
+/* CONFIG_STAT0 register constants (GX, CX) */
+#define CFG_BUS_TYPE 0x00000007
+#define CFG_MEM_TYPE 0x00000038
+#define CFG_INIT_DAC_TYPE 0x00000e00
+
+/* CONFIG_STAT0 register constants (CT, ET, VT) */
+#define CFG_MEM_TYPE_xT 0x00000007
+
+#define ISA 0
+#define EISA 1
+#define LOCAL_BUS 6
+#define PCI 7
+
+/* Memory types for GX, CX */
+#define DRAMx4 0
+#define VRAMx16 1
+#define VRAMx16ssr 2
+#define DRAMx16 3
+#define GraphicsDRAMx16 4
+#define EnhancedVRAMx16 5
+#define EnhancedVRAMx16ssr 6
+
+/* Memory types for CT, ET, VT, GT */
+#define DRAM 1
+#define EDO 2
+#define PSEUDO_EDO 3
+#define SDRAM 4
+#define SGRAM 5
+#define WRAM 6
+
+#define DAC_INTERNAL 0x00
+#define DAC_IBMRGB514 0x01
+#define DAC_ATI68875 0x02
+#define DAC_TVP3026_A 0x72
+#define DAC_BT476 0x03
+#define DAC_BT481 0x04
+#define DAC_ATT20C491 0x14
+#define DAC_SC15026 0x24
+#define DAC_MU9C1880 0x34
+#define DAC_IMSG174 0x44
+#define DAC_ATI68860_B 0x05
+#define DAC_ATI68860_C 0x15
+#define DAC_TVP3026_B 0x75
+#define DAC_STG1700 0x06
+#define DAC_ATT498 0x16
+#define DAC_STG1702 0x07
+#define DAC_SC15021 0x17
+#define DAC_ATT21C498 0x27
+#define DAC_STG1703 0x37
+#define DAC_CH8398 0x47
+#define DAC_ATT20C408 0x57
+
+#define CLK_ATI18818_0 0
+#define CLK_ATI18818_1 1
+#define CLK_STG1703 2
+#define CLK_CH8398 3
+#define CLK_INTERNAL 4
+#define CLK_ATT20C408 5
+#define CLK_IBMRGB514 6
+
+/* MEM_CNTL register constants */
+#define MEM_SIZE_ALIAS 0x00000007
+#define MEM_SIZE_512K 0x00000000
+#define MEM_SIZE_1M 0x00000001
+#define MEM_SIZE_2M 0x00000002
+#define MEM_SIZE_4M 0x00000003
+#define MEM_SIZE_6M 0x00000004
+#define MEM_SIZE_8M 0x00000005
+#define MEM_SIZE_ALIAS_GTB 0x0000000F
+#define MEM_SIZE_2M_GTB 0x00000003
+#define MEM_SIZE_4M_GTB 0x00000007
+#define MEM_SIZE_6M_GTB 0x00000009
+#define MEM_SIZE_8M_GTB 0x0000000B
+#define MEM_BNDRY 0x00030000
+#define MEM_BNDRY_0K 0x00000000
+#define MEM_BNDRY_256K 0x00010000
+#define MEM_BNDRY_512K 0x00020000
+#define MEM_BNDRY_1M 0x00030000
+#define MEM_BNDRY_EN 0x00040000
+
+/* ATI PCI constants */
+#define PCI_ATI_VENDOR_ID 0x1002
+#define PCI_MACH64_GX 0x4758
+#define PCI_MACH64_CX 0x4358
+#define PCI_MACH64_CT 0x4354
+#define PCI_MACH64_ET 0x4554
+#define PCI_MACH64_VT 0x5654
+#define PCI_MACH64_GT 0x4754
+
+/* CONFIG_CHIP_ID register constants */
+#define CFG_CHIP_TYPE 0x0000FFFF
+#define CFG_CHIP_CLASS 0x00FF0000
+#define CFG_CHIP_REV 0xFF000000
+#define CFG_CHIP_VERSION 0x07000000
+#define CFG_CHIP_FOUNDRY 0x38000000
+#define CFG_CHIP_REVISION 0xC0000000
+
+/* Chip IDs read from CONFIG_CHIP_ID */
+#define MACH64_GX_ID 0xD7
+#define MACH64_CX_ID 0x57
+#define MACH64_CT_ID 0x4354
+#define MACH64_ET_ID 0x4554
+#define MACH64_VT_ID 0x5654
+#define MACH64_GT_ID 0x4754
+
+/* Mach64 chip types */
+#define MACH64_UNKNOWN 0
+#define MACH64_GX 1
+#define MACH64_CX 2
+#define MACH64_CT 3
+#define MACH64_ET 4
+#define MACH64_VT 5
+#define MACH64_GT 6
+
+/* DST_CNTL register constants */
+#define DST_X_RIGHT_TO_LEFT 0
+#define DST_X_LEFT_TO_RIGHT 1
+#define DST_Y_BOTTOM_TO_TOP 0
+#define DST_Y_TOP_TO_BOTTOM 2
+#define DST_X_MAJOR 0
+#define DST_Y_MAJOR 4
+#define DST_X_TILE 8
+#define DST_Y_TILE 0x10
+#define DST_LAST_PEL 0x20
+#define DST_POLYGON_ENABLE 0x40
+#define DST_24_ROTATION_ENABLE 0x80
+
+/* SRC_CNTL register constants */
+#define SRC_PATTERN_ENABLE 1
+#define SRC_ROTATION_ENABLE 2
+#define SRC_LINEAR_ENABLE 4
+#define SRC_BYTE_ALIGN 8
+#define SRC_LINE_X_RIGHT_TO_LEFT 0
+#define SRC_LINE_X_LEFT_TO_RIGHT 0x10
+
+/* HOST_CNTL register constants */
+#define HOST_BYTE_ALIGN 1
+
+/* GUI_TRAJ_CNTL register constants */
+#define PAT_MONO_8x8_ENABLE 0x01000000
+#define PAT_CLR_4x2_ENABLE 0x02000000
+#define PAT_CLR_8x1_ENABLE 0x04000000
+
+/* DP_CHAIN_MASK register constants */
+#define DP_CHAIN_4BPP 0x8888
+#define DP_CHAIN_7BPP 0xD2D2
+#define DP_CHAIN_8BPP 0x8080
+#define DP_CHAIN_8BPP_RGB 0x9292
+#define DP_CHAIN_15BPP 0x4210
+#define DP_CHAIN_16BPP 0x8410
+#define DP_CHAIN_24BPP 0x8080
+#define DP_CHAIN_32BPP 0x8080
+
+/* DP_PIX_WIDTH register constants */
+#define DST_1BPP 0
+#define DST_4BPP 1
+#define DST_8BPP 2
+#define DST_15BPP 3
+#define DST_16BPP 4
+#define DST_32BPP 6
+#define SRC_1BPP 0
+#define SRC_4BPP 0x100
+#define SRC_8BPP 0x200
+#define SRC_15BPP 0x300
+#define SRC_16BPP 0x400
+#define SRC_32BPP 0x600
+#define HOST_1BPP 0
+#define HOST_4BPP 0x10000
+#define HOST_8BPP 0x20000
+#define HOST_15BPP 0x30000
+#define HOST_16BPP 0x40000
+#define HOST_32BPP 0x60000
+#define BYTE_ORDER_MSB_TO_LSB 0
+#define BYTE_ORDER_LSB_TO_MSB 0x1000000
+
+/* DP_MIX register constants */
+#define BKGD_MIX_NOT_D 0
+#define BKGD_MIX_ZERO 1
+#define BKGD_MIX_ONE 2
+#define BKGD_MIX_D 3
+#define BKGD_MIX_NOT_S 4
+#define BKGD_MIX_D_XOR_S 5
+#define BKGD_MIX_NOT_D_XOR_S 6
+#define BKGD_MIX_S 7
+#define BKGD_MIX_NOT_D_OR_NOT_S 8
+#define BKGD_MIX_D_OR_NOT_S 9
+#define BKGD_MIX_NOT_D_OR_S 10
+#define BKGD_MIX_D_OR_S 11
+#define BKGD_MIX_D_AND_S 12
+#define BKGD_MIX_NOT_D_AND_S 13
+#define BKGD_MIX_D_AND_NOT_S 14
+#define BKGD_MIX_NOT_D_AND_NOT_S 15
+#define BKGD_MIX_D_PLUS_S_DIV2 0x17
+#define FRGD_MIX_NOT_D 0
+#define FRGD_MIX_ZERO 0x10000
+#define FRGD_MIX_ONE 0x20000
+#define FRGD_MIX_D 0x30000
+#define FRGD_MIX_NOT_S 0x40000
+#define FRGD_MIX_D_XOR_S 0x50000
+#define FRGD_MIX_NOT_D_XOR_S 0x60000
+#define FRGD_MIX_S 0x70000
+#define FRGD_MIX_NOT_D_OR_NOT_S 0x80000
+#define FRGD_MIX_D_OR_NOT_S 0x90000
+#define FRGD_MIX_NOT_D_OR_S 0xa0000
+#define FRGD_MIX_D_OR_S 0xb0000
+#define FRGD_MIX_D_AND_S 0xc0000
+#define FRGD_MIX_NOT_D_AND_S 0xd0000
+#define FRGD_MIX_D_AND_NOT_S 0xe0000
+#define FRGD_MIX_NOT_D_AND_NOT_S 0xf0000
+#define FRGD_MIX_D_PLUS_S_DIV2 0x170000
+
+/* DP_SRC register constants */
+#define BKGD_SRC_BKGD_CLR 0
+#define BKGD_SRC_FRGD_CLR 1
+#define BKGD_SRC_HOST 2
+#define BKGD_SRC_BLIT 3
+#define BKGD_SRC_PATTERN 4
+#define FRGD_SRC_BKGD_CLR 0
+#define FRGD_SRC_FRGD_CLR 0x100
+#define FRGD_SRC_HOST 0x200
+#define FRGD_SRC_BLIT 0x300
+#define FRGD_SRC_PATTERN 0x400
+#define MONO_SRC_ONE 0
+#define MONO_SRC_PATTERN 0x10000
+#define MONO_SRC_HOST 0x20000
+#define MONO_SRC_BLIT 0x30000
+
+/* CLR_CMP_CNTL register constants */
+#define COMPARE_FALSE 0
+#define COMPARE_TRUE 1
+#define COMPARE_NOT_EQUAL 4
+#define COMPARE_EQUAL 5
+#define COMPARE_DESTINATION 0
+#define COMPARE_SOURCE 0x1000000
+
+/* FIFO_STAT register constants */
+#define FIFO_ERR 0x80000000
+
+/* CONTEXT_LOAD_CNTL constants */
+#define CONTEXT_NO_LOAD 0
+#define CONTEXT_LOAD 0x10000
+#define CONTEXT_LOAD_AND_DO_FILL 0x20000
+#define CONTEXT_LOAD_AND_DO_LINE 0x30000
+#define CONTEXT_EXECUTE 0
+#define CONTEXT_CMD_DISABLE 0x80000000
+
+/* GUI_STAT register constants */
+#define ENGINE_IDLE 0
+#define ENGINE_BUSY 1
+#define SCISSOR_LEFT_FLAG 0x10
+#define SCISSOR_RIGHT_FLAG 0x20
+#define SCISSOR_TOP_FLAG 0x40
+#define SCISSOR_BOTTOM_FLAG 0x80
+
+/* ATI VGA Extended Regsiters */
+#define sioATIEXT 0x1ce
+#define bioATIEXT 0x3ce
+
+#define ATI2E 0xae
+#define ATI32 0xb2
+#define ATI36 0xb6
+
+/* VGA Graphics Controller Registers */
+#define VGAGRA 0x3ce
+#define GRA06 0x06
+
+/* VGA Seququencer Registers */
+#define VGASEQ 0x3c4
+#define SEQ02 0x02
+#define SEQ04 0x04
+
+#define MACH64_MAX_X ENGINE_MAX_X
+#define MACH64_MAX_Y ENGINE_MAX_Y
+
+#define INC_X 0x0020
+#define INC_Y 0x0080
+
+#define RGB16_555 0x0000
+#define RGB16_565 0x0040
+#define RGB16_655 0x0080
+#define RGB16_664 0x00c0
+
+#define POLY_TEXT_TYPE 0x0001
+#define IMAGE_TEXT_TYPE 0x0002
+#define TEXT_TYPE_8_BIT 0x0004
+#define TEXT_TYPE_16_BIT 0x0008
+#define POLY_TEXT_TYPE_8 (POLY_TEXT_TYPE | TEXT_TYPE_8_BIT)
+#define IMAGE_TEXT_TYPE_8 (IMAGE_TEXT_TYPE | TEXT_TYPE_8_BIT)
+#define POLY_TEXT_TYPE_16 (POLY_TEXT_TYPE | TEXT_TYPE_16_BIT)
+#define IMAGE_TEXT_TYPE_16 (IMAGE_TEXT_TYPE | TEXT_TYPE_16_BIT)
+
+#define MACH64_NUM_CLOCKS 16
+#define MACH64_NUM_FREQS 50
+
+/* Wait until "v" queue entries are free */
+#define aty_WaitQueue(v) { while ((aty_ld_le32(FIFO_STAT) & 0xffff) > \
+ ((unsigned short)(0x8000 >> (v)))); }
+
+/* Wait until GP is idle and queue is empty */
+#define aty_WaitIdleEmpty() { aty_WaitQueue(16); \
+ while ((aty_ld_le32(GUI_STAT) & 1) != 0); }
+
+#define SKIP_2(_v) ((((_v)<<1)&0xfff8)|((_v)&0x3)|(((_v)&0x80)>>5))
+
+#define MACH64_BIT_BLT(_srcx, _srcy, _dstx, _dsty, _w, _h, _dir) \
+{ \
+ aty_WaitQueue(5); \
+ aty_st_le32(SRC_Y_X, (((_srcx) << 16) | ((_srcy) & 0x0000ffff))); \
+ aty_st_le32(SRC_WIDTH1, (_w)); \
+ aty_st_le32(DST_CNTL, (_dir)); \
+ aty_st_le32(DST_Y_X, (((_dstx) << 16) | ((_dsty) & 0x0000ffff))); \
+ aty_st_le32(DST_HEIGHT_WIDTH, (((_w) << 16) | ((_h) & 0x0000ffff))); \
+}
+#endif /* REGMACH64_H */
+
diff --git a/drivers/video/atyfb.c b/drivers/video/atyfb.c
new file mode 100644
index 000000000..e1f8b3ef4
--- /dev/null
+++ b/drivers/video/atyfb.c
@@ -0,0 +1,1685 @@
+/*
+ * linux/drivers/video/atyfb.c -- Frame buffer device for ATI/Open Firmware
+ *
+ * Copyright (C) 1997 Geert Uytterhoeven
+ *
+ * This driver is partly based on the PowerMac console driver:
+ *
+ * Copyright (C) 1996 Paul Mackerras
+ *
+ * and on the PowerMac ATI/mach64 display driver:
+ *
+ * Copyright (C) 1997 Michael AK Tesch
+ *
+ * with work by Jon Howell
+ * Harry AC Eaton
+ * Anthony Tong <atong@uiuc.edu>
+ *
+ * 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.
+ */
+
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/mm.h>
+#include <linux/tty.h>
+#include <linux/malloc.h>
+#include <linux/vmalloc.h>
+#include <linux/delay.h>
+#include <linux/interrupt.h>
+#include <linux/fb.h>
+#include <linux/selection.h>
+#include <linux/init.h>
+#include <linux/pci.h>
+#include <linux/nvram.h>
+#include <linux/vc_ioctl.h>
+#include <asm/io.h>
+#include <asm/prom.h>
+#include <asm/pci-bridge.h>
+
+#include "aty.h"
+#include "fbcon.h"
+#include "fbcon-cfb8.h"
+#include "fbcon-cfb16.h"
+#include "fbcon-cfb32.h"
+
+
+static int currcon = 0;
+static struct display fb_disp;
+static struct fb_info fb_info;
+static struct { u_char red, green, blue, pad; } palette[256];
+
+static char atyfb_name[16] = "ATY Mach64";
+
+struct atyfb_par {
+ int vmode;
+ int cmode;
+ u_int vxres; /* virtual screen size */
+ u_int vyres;
+ int xoffset; /* virtual screen position */
+ int yoffset;
+};
+
+
+/*
+ * Video mode values.
+ * These are supposed to be the same as the values that
+ * Apple uses in MacOS.
+ */
+#define VMODE_NVRAM 0 /* use value stored in nvram */
+#define VMODE_512_384_60I 1 /* 512x384, 60Hz interlaced (NTSC) */
+#define VMODE_512_384_60 2 /* 512x384, 60Hz */
+#define VMODE_640_480_50I 3 /* 640x480, 50Hz interlaced (PAL) */
+#define VMODE_640_480_60I 4 /* 640x480, 60Hz interlaced (NTSC) */
+#define VMODE_640_480_60 5 /* 640x480, 60Hz (VGA) */
+#define VMODE_640_480_67 6 /* 640x480, 67Hz */
+#define VMODE_640_870_75P 7 /* 640x870, 75Hz (portrait) */
+#define VMODE_768_576_50I 8 /* 768x576, 50Hz (PAL full frame) */
+#define VMODE_800_600_56 9 /* 800x600, 56Hz */
+#define VMODE_800_600_60 10 /* 800x600, 60Hz */
+#define VMODE_800_600_72 11 /* 800x600, 72Hz */
+#define VMODE_800_600_75 12 /* 800x600, 75Hz */
+#define VMODE_832_624_75 13 /* 832x624, 75Hz */
+#define VMODE_1024_768_60 14 /* 1024x768, 60Hz */
+#define VMODE_1024_768_70 15 /* 1024x768, 70Hz (or 72Hz?) */
+#define VMODE_1024_768_75V 16 /* 1024x768, 75Hz (VESA) */
+#define VMODE_1024_768_75 17 /* 1024x768, 75Hz */
+#define VMODE_1152_870_75 18 /* 1152x870, 75Hz */
+#define VMODE_1280_960_75 19 /* 1280x960, 75Hz */
+#define VMODE_1280_1024_75 20 /* 1280x1024, 75Hz */
+#define VMODE_MAX 20
+#define VMODE_CHOOSE 99 /* choose based on monitor sense */
+
+/*
+ * Color mode values, used to select number of bits/pixel.
+ */
+#define CMODE_NVRAM -1 /* use value stored in nvram */
+#define CMODE_8 0 /* 8 bits/pixel */
+#define CMODE_16 1 /* 16 (actually 15) bits/pixel */
+#define CMODE_32 2 /* 32 (actually 24) bits/pixel */
+
+
+static int default_video_mode = VMODE_NVRAM;
+static int default_color_mode = CMODE_NVRAM;
+
+static struct atyfb_par default_par;
+static struct atyfb_par current_par;
+
+
+/*
+ * Addresses in NVRAM where video mode and pixel size are stored.
+ */
+#define NV_VMODE 0x140f
+#define NV_CMODE 0x1410
+
+/*
+ * Horizontal and vertical resolution information.
+ */
+extern struct vmode_attr {
+ int hres;
+ int vres;
+ int vfreq;
+ int interlaced;
+} vmode_attrs[VMODE_MAX];
+
+
+/*
+ * Horizontal and vertical resolution for each mode.
+ */
+static struct vmode_attr vmode_attrs[VMODE_MAX] = {
+ {512, 384, 60, 1},
+ {512, 384, 60},
+ {640, 480, 50, 1},
+ {640, 480, 60, 1},
+ {640, 480, 60},
+ {640, 480, 67},
+ {640, 870, 75},
+ {768, 576, 50, 1},
+ {800, 600, 56},
+ {800, 600, 60},
+ {800, 600, 72},
+ {800, 600, 75},
+ {832, 624, 75},
+ {1024, 768, 60},
+ {1024, 768, 72},
+ {1024, 768, 75},
+ {1024, 768, 75},
+ {1152, 870, 75},
+ {1280, 960, 75},
+ {1280, 1024, 75}
+};
+
+
+/*
+ * We get a sense value from the monitor and use it to choose
+ * what resolution to use. This structure maps sense values
+ * to display mode values (which determine the resolution and
+ * frequencies).
+ */
+static struct mon_map {
+ int sense;
+ int vmode;
+} monitor_map [] = {
+ {0x000, VMODE_1280_1024_75}, /* 21" RGB */
+ {0x114, VMODE_640_870_75P}, /* Portrait Monochrome */
+ {0x221, VMODE_512_384_60}, /* 12" RGB*/
+ {0x331, VMODE_1280_1024_75}, /* 21" RGB (Radius) */
+ {0x334, VMODE_1280_1024_75}, /* 21" mono (Radius) */
+ {0x335, VMODE_1280_1024_75}, /* 21" mono */
+ {0x40A, VMODE_640_480_60I}, /* NTSC */
+ {0x51E, VMODE_640_870_75P}, /* Portrait RGB */
+ {0x603, VMODE_832_624_75}, /* 12"-16" multiscan */
+ {0x60b, VMODE_1024_768_70}, /* 13"-19" multiscan */
+ {0x623, VMODE_1152_870_75}, /* 13"-21" multiscan */
+ {0x62b, VMODE_640_480_67}, /* 13"/14" RGB */
+ {0x700, VMODE_640_480_50I}, /* PAL */
+ {0x714, VMODE_640_480_60I}, /* NTSC */
+ {0x717, VMODE_800_600_75}, /* VGA */
+ {0x72d, VMODE_832_624_75}, /* 16" RGB (Goldfish) */
+ {0x730, VMODE_768_576_50I}, /* PAL (Alternate) */
+ {0x73a, VMODE_1152_870_75}, /* 3rd party 19" */
+ {-1, VMODE_640_480_60}, /* catch-all, must be last */
+};
+
+static int map_monitor_sense(int sense)
+{
+ struct mon_map *map;
+
+ for (map = monitor_map; map->sense >= 0; ++map)
+ if (map->sense == sense)
+ break;
+ return map->vmode;
+}
+
+struct aty_cmap_regs {
+ unsigned char windex;
+ unsigned char lut;
+ unsigned char mask;
+ unsigned char rindex;
+ unsigned char cntl;
+};
+
+typedef struct aty_regvals {
+ int offset[3]; /* first pixel address */
+
+ int crtc_h_sync_strt_wid[3]; /* depth dependant */
+ int crtc_gen_cntl[3];
+ int mem_cntl[3];
+
+ int crtc_h_tot_disp; /* mode dependant */
+ int crtc_v_tot_disp;
+ int crtc_v_sync_strt_wid;
+ int crtc_off_pitch;
+
+ unsigned char clock_val[2]; /* vals for 20 and 21 */
+} aty_regvals;
+
+struct rage_regvals {
+ int h_total, h_sync_start, h_sync_width;
+ int v_total, v_sync_start, v_sync_width;
+ int h_sync_neg, v_sync_neg;
+};
+
+static int aty_vram_reqd(const struct atyfb_par *par);
+static struct aty_regvals *get_aty_struct(int vmode);
+
+static unsigned long frame_buffer;
+
+static int total_vram; /* total amount of video memory, bytes */
+static int chip_type; /* what chip type was detected */
+
+static unsigned long ati_regbase;
+static struct aty_cmap_regs *aty_cmap_regs;
+
+#include "ati-gx.h"
+#include "ati-gt.h"
+#include "ati-vt.h"
+
+static struct aty_regvals *aty_gt_reg_init[20] = {
+ NULL, NULL, NULL, NULL,
+ &aty_gt_reg_init_5,
+ &aty_gt_reg_init_6,
+ NULL, NULL,
+ &aty_gt_reg_init_9,
+ &aty_gt_reg_init_10,
+ &aty_gt_reg_init_11,
+ &aty_gt_reg_init_12,
+ &aty_gt_reg_init_13,
+ &aty_gt_reg_init_14,
+ &aty_gt_reg_init_15,
+ NULL,
+ &aty_gt_reg_init_17,
+ &aty_gt_reg_init_18,
+ NULL,
+ &aty_gt_reg_init_20
+};
+
+static struct aty_regvals *aty_gx_reg_init[20] = {
+ NULL, NULL, NULL, NULL,
+ &aty_gx_reg_init_6,
+ &aty_gx_reg_init_6,
+ NULL, NULL, NULL, NULL, NULL, NULL,
+ &aty_gx_reg_init_13,
+ &aty_gx_reg_init_14,
+ &aty_gx_reg_init_15,
+ NULL,
+ &aty_gx_reg_init_17,
+ &aty_gx_reg_init_18,
+ NULL,
+ &aty_gx_reg_init_20
+};
+
+static struct aty_regvals *aty_vt_reg_init[21] = {
+ NULL, NULL, NULL, NULL,
+ &aty_vt_reg_init_5,
+ &aty_vt_reg_init_6,
+ NULL, NULL, NULL,
+ &aty_vt_reg_init_10,
+ &aty_vt_reg_init_11,
+ &aty_vt_reg_init_12,
+ &aty_vt_reg_init_13,
+ &aty_vt_reg_init_14,
+ &aty_vt_reg_init_15,
+ NULL,
+ &aty_vt_reg_init_17,
+ &aty_vt_reg_init_18,
+ &aty_vt_reg_init_19,
+ &aty_vt_reg_init_20
+};
+
+ /*
+ * Interface used by the world
+ */
+
+unsigned long atyfb_init(unsigned long mem_start);
+void atyfb_setup(char *options, int *ints);
+
+static int atyfb_open(struct fb_info *info);
+static int atyfb_release(struct fb_info *info);
+static int atyfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int atyfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int atyfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int atyfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int atyfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int atyfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int atyfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info);
+
+
+ /*
+ * Interface to the low level console driver
+ */
+
+static int atyfbcon_switch(int con, struct fb_info *info);
+static int atyfbcon_updatevar(int con, struct fb_info *info);
+static void atyfbcon_blank(int blank, struct fb_info *info);
+
+
+ /*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static struct display_switch fbcon_aty8;
+#endif
+
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+extern struct vc_mode display_info;
+extern struct fb_info *console_fb_info;
+extern int (*console_setmode_ptr)(struct vc_mode *, int);
+extern int (*console_set_cmap_ptr)(struct fb_cmap *, int, int,
+ struct fb_info *);
+static int atyfb_console_setmode(struct vc_mode *, int);
+#endif
+
+
+ /*
+ * Internal routines
+ */
+
+static int atyfb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info);
+static int atyfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info);
+static void do_install_cmap(int con, struct fb_info *info);
+
+
+static struct fb_ops atyfb_ops = {
+ atyfb_open, atyfb_release, atyfb_get_fix, atyfb_get_var, atyfb_set_var,
+ atyfb_get_cmap, atyfb_set_cmap, atyfb_pan_display, NULL, atyfb_ioctl
+};
+
+
+static inline int aty_vram_reqd(const struct atyfb_par *par)
+{
+ return (par->vxres*par->vyres) << par->cmode;
+}
+
+extern inline unsigned aty_ld_le32(volatile unsigned long addr)
+{
+ register unsigned long temp = ati_regbase,val;
+
+ asm("lwbrx %0,%1,%2": "=r"(val):"r"(addr), "r"(temp));
+ return val;
+}
+
+extern inline void aty_st_le32(volatile unsigned long addr, unsigned val)
+{
+ register unsigned long temp = ati_regbase;
+
+ asm("stwbrx %0,%1,%2": : "r"(val), "r"(addr), "r"(temp):"memory");
+}
+
+extern inline unsigned char aty_ld_8(volatile unsigned long addr)
+{
+ return *(char *) ((long) addr + (long) ati_regbase);
+}
+
+extern inline void aty_st_8(volatile unsigned long addr, unsigned char val)
+{
+ *(unsigned char *) (addr + (unsigned long) ati_regbase) = val;
+}
+
+static void aty_st_514(int offset, char val)
+{
+ aty_WaitQueue(5);
+ aty_st_8(DAC_CNTL, 1);
+ aty_st_8(DAC_W_INDEX, offset & 0xff); /* right addr byte */
+ aty_st_8(DAC_DATA, (offset >> 8) & 0xff); /* left addr byte */
+ eieio();
+ aty_st_8(DAC_MASK, val);
+ eieio();
+ aty_st_8(DAC_CNTL, 0);
+}
+
+static void aty_st_pll(int offset, char val)
+{
+ aty_WaitQueue(3);
+ aty_st_8(CLOCK_CNTL + 1, (offset << 2) | PLL_WR_EN); /* write addr byte */
+ eieio();
+ aty_st_8(CLOCK_CNTL + 2, val); /* write the register value */
+ eieio();
+ aty_st_8(CLOCK_CNTL + 1, (offset << 2) & ~PLL_WR_EN);
+}
+
+static struct aty_regvals *get_aty_struct(int vmode)
+{
+ int v = vmode - 1;
+
+ switch (chip_type) {
+ case MACH64_GT_ID:
+ return aty_gt_reg_init[v];
+ break;
+ case MACH64_VT_ID:
+ return aty_vt_reg_init[v];
+ break;
+ default: /* default to MACH64_GX_ID */
+ return aty_gx_reg_init[v];
+ break;
+ }
+}
+
+static int read_aty_sense(void)
+{
+ int sense, i;
+
+ aty_st_le32(GP_IO, 0x31003100); /* drive outputs high */
+ __delay(200);
+ aty_st_le32(GP_IO, 0); /* turn off outputs */
+ __delay(2000);
+ i = aty_ld_le32(GP_IO); /* get primary sense value */
+ sense = ((i & 0x3000) >> 3) | (i & 0x100);
+
+ /* drive each sense line low in turn and collect the other 2 */
+ aty_st_le32(GP_IO, 0x20000000); /* drive A low */
+ __delay(2000);
+ i = aty_ld_le32(GP_IO);
+ sense |= ((i & 0x1000) >> 7) | ((i & 0x100) >> 4);
+ aty_st_le32(GP_IO, 0x20002000); /* drive A high again */
+ __delay(200);
+
+ aty_st_le32(GP_IO, 0x10000000); /* drive B low */
+ __delay(2000);
+ i = aty_ld_le32(GP_IO);
+ sense |= ((i & 0x2000) >> 10) | ((i & 0x100) >> 6);
+ aty_st_le32(GP_IO, 0x10001000); /* drive B high again */
+ __delay(200);
+
+ aty_st_le32(GP_IO, 0x01000000); /* drive C low */
+ __delay(2000);
+ sense |= (aty_ld_le32(GP_IO) & 0x3000) >> 12;
+ aty_st_le32(GP_IO, 0); /* turn off outputs */
+
+ return sense;
+}
+
+static void RGB514_Program(int cmode)
+{
+ typedef struct {
+ char pixel_dly;
+ char misc2_cntl;
+ char pixel_rep;
+ char pixel_cntl_index;
+ char pixel_cntl_v1;
+ } RGB514_DAC_Table;
+
+ static RGB514_DAC_Table RGB514DAC_Tab[8] = {
+ {0, 0x41, 0x03, 0x71, 0x45}, // 8bpp
+ {0, 0x45, 0x04, 0x0c, 0x01}, // 555
+ {0, 0x45, 0x06, 0x0e, 0x00}, // XRGB
+ };
+ RGB514_DAC_Table *pDacProgTab;
+
+ pDacProgTab = &RGB514DAC_Tab[cmode];
+
+ aty_st_514(0x90, 0x00);
+ aty_st_514(0x04, pDacProgTab->pixel_dly);
+ aty_st_514(0x05, 0x00);
+
+ aty_st_514(0x2, 0x1);
+ aty_st_514(0x71, pDacProgTab->misc2_cntl);
+ aty_st_514(0x0a, pDacProgTab->pixel_rep);
+
+ aty_st_514(pDacProgTab->pixel_cntl_index, pDacProgTab->pixel_cntl_v1);
+}
+
+static void set_off_pitch(const struct atyfb_par *par)
+{
+ u32 pitch, offset;
+
+ pitch = par->vxres>>3;
+ offset = ((par->yoffset*par->vxres+par->xoffset)>>3)<<par->cmode;
+ aty_st_le32(CRTC_OFF_PITCH, pitch<<22 | offset);
+ if (chip_type == MACH64_GT_ID) {
+ /* Is this OK for other chips? */
+ aty_st_le32(DST_OFF_PITCH, pitch<<22 | offset);
+ aty_st_le32(SRC_OFF_PITCH, pitch<<22 | offset);
+ }
+}
+
+static void atyfb_set_par(struct atyfb_par *par)
+{
+ int i, hres;
+ struct aty_regvals *init = get_aty_struct(par->vmode);
+ int vram_type = aty_ld_le32(CONFIG_STAT0) & 7;
+
+ if (init == 0) /* paranoia, shouldn't get here */
+ panic("aty: display mode %d not supported", par->vmode);
+
+ current_par = *par;
+ hres = vmode_attrs[par->vmode-1].hres;
+
+ /* clear FIFO errors */
+ aty_st_le32(BUS_CNTL, aty_ld_le32(BUS_CNTL) | BUS_HOST_ERR_ACK
+ | BUS_FIFO_ERR_ACK);
+
+ /* Reset engine */
+ i = aty_ld_le32(GEN_TEST_CNTL);
+ aty_st_le32(GEN_TEST_CNTL, i & ~GUI_ENGINE_ENABLE);
+ eieio();
+ aty_WaitIdleEmpty();
+ aty_st_le32(GEN_TEST_CNTL, i | GUI_ENGINE_ENABLE);
+ aty_WaitIdleEmpty();
+
+ if ( chip_type != MACH64_GT_ID ) {
+ i = aty_ld_le32(CRTC_GEN_CNTL);
+ aty_st_le32(CRTC_GEN_CNTL, i | CRTC_EXT_DISP_EN);
+ }
+
+ if ( chip_type == MACH64_GX_ID ) {
+ i = aty_ld_le32(GEN_TEST_CNTL);
+ aty_st_le32(GEN_TEST_CNTL, i | GEN_OVR_OUTPUT_EN );
+ }
+
+ switch (chip_type) {
+ case MACH64_VT_ID:
+ aty_st_pll(PLL_MACRO_CNTL, 0xb5);
+ aty_st_pll(PLL_REF_DIV, 0x2d);
+ aty_st_pll(PLL_GEN_CNTL, 0x14);
+ aty_st_pll(MCLK_FB_DIV, 0xbd);
+ aty_st_pll(PLL_VCLK_CNTL, 0x0b);
+ aty_st_pll(VCLK_POST_DIV, init->clock_val[0]);
+ aty_st_pll(VCLK0_FB_DIV, init->clock_val[1]);
+ aty_st_pll(VCLK1_FB_DIV, 0xd6);
+ aty_st_pll(VCLK2_FB_DIV, 0xee);
+ aty_st_pll(VCLK3_FB_DIV, 0xf8);
+ aty_st_pll(PLL_XCLK_CNTL, 0x0);
+ aty_st_pll(PLL_TEST_CTRL, 0x0);
+ aty_st_pll(PLL_TEST_COUNT, 0x0);
+ break;
+ case MACH64_GT_ID:
+ if (vram_type == 5) {
+ aty_st_pll(0, 0xcd);
+ aty_st_pll(PLL_MACRO_CNTL,
+ par->vmode >= VMODE_1024_768_60 ? 0xd3: 0xd5);
+ aty_st_pll(PLL_REF_DIV, 0x21);
+ aty_st_pll(PLL_GEN_CNTL, 0x44);
+ aty_st_pll(MCLK_FB_DIV, 0xe8);
+ aty_st_pll(PLL_VCLK_CNTL, 0x03);
+ aty_st_pll(VCLK_POST_DIV, init->offset[0]);
+ aty_st_pll(VCLK0_FB_DIV, init->offset[1]);
+ aty_st_pll(VCLK1_FB_DIV, 0x8e);
+ aty_st_pll(VCLK2_FB_DIV, 0x9e);
+ aty_st_pll(VCLK3_FB_DIV, 0xc6);
+ aty_st_pll(PLL_XCLK_CNTL, init->offset[2]);
+ aty_st_pll(12, 0xa6);
+ aty_st_pll(13, 0x1b);
+ } else {
+ aty_st_pll(PLL_MACRO_CNTL, 0xd5);
+ aty_st_pll(PLL_REF_DIV, 0x21);
+ aty_st_pll(PLL_GEN_CNTL, 0xc4);
+ aty_st_pll(MCLK_FB_DIV, 0xda);
+ aty_st_pll(PLL_VCLK_CNTL, 0x03);
+ /* offset actually holds clock values */
+ aty_st_pll(VCLK_POST_DIV, init->offset[0]);
+ aty_st_pll(VCLK0_FB_DIV, init->offset[1]);
+ aty_st_pll(VCLK1_FB_DIV, 0x8e);
+ aty_st_pll(VCLK2_FB_DIV, 0x9e);
+ aty_st_pll(VCLK3_FB_DIV, 0xc6);
+ aty_st_pll(PLL_TEST_CTRL, 0x0);
+ aty_st_pll(PLL_XCLK_CNTL, init->offset[2]);
+ aty_st_pll(12, 0xa0);
+ aty_st_pll(13, 0x1b);
+ }
+ break;
+ default:
+ RGB514_Program(par->cmode);
+ aty_WaitIdleEmpty();
+ aty_st_514(0x06, 0x02);
+ aty_st_514(0x10, 0x01);
+ aty_st_514(0x70, 0x01);
+ aty_st_514(0x8f, 0x1f);
+ aty_st_514(0x03, 0x00);
+ aty_st_514(0x05, 0x00);
+ aty_st_514(0x20, init->clock_val[0]);
+ aty_st_514(0x21, init->clock_val[1]);
+ break;
+ }
+
+ aty_ld_8(DAC_REGS); /* clear counter */
+ aty_WaitIdleEmpty();
+
+ aty_st_le32(CRTC_H_TOTAL_DISP, init->crtc_h_tot_disp);
+ aty_st_le32(CRTC_H_SYNC_STRT_WID, init->crtc_h_sync_strt_wid[par->cmode]);
+ aty_st_le32(CRTC_V_TOTAL_DISP, init->crtc_v_tot_disp);
+ aty_st_le32(CRTC_V_SYNC_STRT_WID, init->crtc_v_sync_strt_wid);
+
+ aty_st_8(CLOCK_CNTL, 0);
+ aty_st_8(CLOCK_CNTL, CLOCK_STROBE);
+
+ aty_st_le32(CRTC_VLINE_CRNT_VLINE, 0);
+
+ set_off_pitch(par);
+
+ if (chip_type == MACH64_GT_ID) {
+ aty_st_le32(BUS_CNTL, 0x7b23a040);
+
+ /* need to set DSP values !! assume sdram */
+ i = init->crtc_gen_cntl[0] - (0x100000 * par->cmode);
+ if ( vram_type == 5 )
+ i = init->crtc_gen_cntl[1] - (0x100000 * par->cmode);
+ aty_st_le32(DSP_CONFIG, i);
+
+ i = aty_ld_le32(MEM_CNTL) & MEM_SIZE_ALIAS;
+ if ( vram_type == 5 ) {
+ i |= ((1 * par->cmode) << 26) | 0x4215b0;
+ aty_st_le32(DSP_ON_OFF,sgram_dsp[par->vmode-1][par->cmode]);
+
+ //aty_st_le32(CLOCK_CNTL,8192);
+ } else {
+ i |= ((1 * par->cmode) << 26) | 0x300090;
+ aty_st_le32(DSP_ON_OFF, init->mem_cntl[par->cmode]);
+ }
+
+ aty_st_le32(MEM_CNTL, i);
+ aty_st_le32(EXT_MEM_CNTL, 0x5000001);
+
+ /* if (total_vram > 0x400000)
+ i |= 0x538; this not been verified on > 4Megs!! */
+ } else {
+
+/* The magic constant below translates into:
+* 5 = No RDY delay, 1 wait st for mem write, increment during burst transfer
+* 9 = DAC access delayed, 1 wait state for DAC
+* 0 = Disables interupts for FIFO errors
+* e = Allows FIFO to generate 14 wait states before generating error
+* 1 = DAC snooping disabled, ROM disabled
+* 0 = ROM page at 0 (disabled so doesn't matter)
+* f = 15 ROM wait states (disabled so doesn't matter)
+* f = 15 BUS wait states (I'm not sure this applies to PCI bus types)
+* at some point it would be good to experiment with bench marks to see if
+* we can gain some speed by fooling with the wait states etc.
+*/
+ if (chip_type == MACH64_VT_ID)
+ aty_st_le32(BUS_CNTL, 0x680000f9);
+ else
+ aty_st_le32(BUS_CNTL, 0x590e10ff);
+
+ switch (total_vram) {
+ case 0x00100000:
+ aty_st_le32(MEM_CNTL, vt_mem_cntl[0][par->cmode]);
+ break;
+ case 0x00200000:
+ aty_st_le32(MEM_CNTL, vt_mem_cntl[1][par->cmode]);
+ break;
+ case 0x00400000:
+ aty_st_le32(MEM_CNTL, vt_mem_cntl[2][par->cmode]);
+ break;
+ default:
+ i = aty_ld_le32(MEM_CNTL) & 0x000F;
+ aty_st_le32(MEM_CNTL,
+ (init->mem_cntl[par->cmode] & 0xFFFFFFF0) | i);
+ }
+ }
+/* These magic constants are harder to figure out
+* on the vt chipset bit 2 set makes the screen brighter
+* and bit 15 makes the screen black! But nothing else
+* seems to matter for the vt DAC_CNTL
+*/
+ switch (chip_type) {
+ case MACH64_GT_ID:
+ i = 0x86010102;
+ break;
+ case MACH64_VT_ID:
+ i = 0x87010184;
+ break;
+ default:
+ i = 0x47012100;
+ break;
+ }
+
+ aty_st_le32(DAC_CNTL, i);
+ aty_st_8(DAC_MASK, 0xff);
+
+ switch (par->cmode) {
+ case CMODE_16:
+ i = CRTC_PIX_WIDTH_15BPP; break;
+ /*case CMODE_24: */
+ case CMODE_32:
+ i = CRTC_PIX_WIDTH_32BPP; break;
+ case CMODE_8:
+ default:
+ i = CRTC_PIX_WIDTH_8BPP; break;
+ }
+
+ if (chip_type != MACH64_GT_ID) {
+ aty_st_le32(CRTC_INT_CNTL, 0x00000002);
+ aty_st_le32(GEN_TEST_CNTL, GUI_ENGINE_ENABLE | BLOCK_WRITE_ENABLE); /* gui_en block_en */
+ i |= init->crtc_gen_cntl[par->cmode];
+ }
+ /* Gentlemen, start your crtc engine */
+ aty_st_le32(CRTC_GEN_CNTL, CRTC_EXT_DISP_EN | CRTC_ENABLE | i);
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+ display_info.height = vmode_attrs[par->vmode-1].vres;
+ display_info.width = vmode_attrs[par->vmode-1].hres;
+ display_info.depth = 8<<par->cmode;
+ display_info.pitch = par->vxres<<par->cmode;
+ display_info.mode = par->vmode;
+ strcpy(display_info.name, atyfb_name);
+ display_info.fb_address =
+ iopa(((chip_type != MACH64_GT_ID) ?
+ frame_buffer + init->offset[par->cmode] : frame_buffer));
+ display_info.cmap_adr_address = iopa((unsigned long)&aty_cmap_regs->windex);
+ display_info.cmap_data_address = iopa((unsigned long)&aty_cmap_regs->lut);
+ display_info.disp_reg_address = iopa(ati_regbase);
+#endif /* CONFIG_FB_COMPAT_XPMAC) */
+}
+
+
+ /*
+ * Open/Release the frame buffer device
+ */
+
+static int atyfb_open(struct fb_info *info)
+
+{
+ /*
+ * Nothing, only a usage count for the moment
+ */
+
+ MOD_INC_USE_COUNT;
+ return(0);
+}
+
+static int atyfb_release(struct fb_info *info)
+{
+ MOD_DEC_USE_COUNT;
+ return(0);
+}
+
+
+static int encode_fix(struct fb_fix_screeninfo *fix,
+ const struct atyfb_par *par)
+{
+ struct aty_regvals *init;
+
+ memset(fix, 0, sizeof(struct fb_fix_screeninfo));
+
+ strcpy(fix->id, atyfb_name);
+ init = get_aty_struct(par->vmode);
+ /*
+ * FIXME: This will cause problems on non-GT chips, because the frame
+ * buffer must be aligned to a page
+ */
+ fix->smem_start = (char *)((chip_type != MACH64_GT_ID)
+ ? frame_buffer + init->offset[par->cmode] : frame_buffer);
+ fix->smem_len = (u32)total_vram;
+ if (fix->smem_len > 0x7ff000)
+ fix->smem_len = 0x7ff000; /* last page is MMIO */
+ fix->mmio_start = (char *)(ati_regbase & ~0xfff);
+ fix->mmio_len = 4096;
+ fix->type = FB_TYPE_PACKED_PIXELS;
+ fix->type_aux = 0;
+ fix->line_length = par->vxres<<par->cmode;
+ fix->visual = par->cmode == CMODE_8 ? FB_VISUAL_PSEUDOCOLOR
+ : FB_VISUAL_TRUECOLOR;
+ fix->ywrapstep = 0;
+ fix->xpanstep = 8;
+ fix->ypanstep = 1;
+
+ return 0;
+}
+
+
+static int decode_var(struct fb_var_screeninfo *var,
+ struct atyfb_par *par)
+{
+ int xres = var->xres;
+ int yres = var->yres;
+ int bpp = var->bits_per_pixel;
+ struct aty_regvals *init;
+
+ /* This should support more video modes */
+
+ if (xres <= 512 && yres <= 384)
+ par->vmode = VMODE_512_384_60; /* 512x384, 60Hz */
+ else if (xres <= 640 && yres <= 480)
+ par->vmode = VMODE_640_480_67; /* 640x480, 67Hz */
+ else if (xres <= 640 && yres <= 870)
+ par->vmode = VMODE_640_870_75P; /* 640x870, 75Hz (portrait) */
+ else if (xres <= 768 && yres <= 576)
+ par->vmode = VMODE_768_576_50I; /* 768x576, 50Hz (PAL full frame) */
+ else if (xres <= 800 && yres <= 600)
+ par->vmode = VMODE_800_600_75; /* 800x600, 75Hz */
+ else if (xres <= 832 && yres <= 624)
+ par->vmode = VMODE_832_624_75; /* 832x624, 75Hz */
+ else if (xres <= 1024 && yres <= 768)
+ par->vmode = VMODE_1024_768_75; /* 1024x768, 75Hz */
+ else if (xres <= 1152 && yres <= 870)
+ par->vmode = VMODE_1152_870_75; /* 1152x870, 75Hz */
+ else if (xres <= 1280 && yres <= 960)
+ par->vmode = VMODE_1280_960_75; /* 1280x960, 75Hz */
+ else if (xres <= 1280 && yres <= 1024)
+ par->vmode = VMODE_1280_1024_75; /* 1280x1024, 75Hz */
+ else
+ return -EINVAL;
+
+ xres = vmode_attrs[par->vmode-1].hres;
+ yres = vmode_attrs[par->vmode-1].vres;
+
+ if (var->xres_virtual <= xres)
+ par->vxres = xres;
+ else
+ par->vxres = (var->xres_virtual+7) & ~7;
+ if (var->yres_virtual <= yres)
+ par->vyres = yres;
+ else
+ par->vyres = var->yres_virtual;
+
+ par->xoffset = (var->xoffset+7) & ~7;
+ par->yoffset = var->yoffset;
+ if (par->xoffset+xres > par->vxres || par->yoffset+yres > par->vyres)
+ return -EINVAL;
+
+ if (bpp <= 8)
+ par->cmode = CMODE_8;
+ else if (bpp <= 16)
+ par->cmode = CMODE_16;
+ else if (bpp <= 32)
+ par->cmode = CMODE_32;
+ else
+ return -EINVAL;
+
+ if (aty_vram_reqd(par) > total_vram)
+ return -EINVAL;
+
+ /* Check if we know about the wanted video mode */
+ init = get_aty_struct(par->vmode);
+ if (init == NULL || init->crtc_h_sync_strt_wid[par->cmode] == 0 ||
+ (chip_type != MACH64_GT_ID &&
+ init->crtc_gen_cntl[par->cmode] == 0) ||
+ (chip_type == MACH64_GT_ID && (aty_ld_le32(CONFIG_STAT0) & 7) == 5 &&
+ init->crtc_gen_cntl[1] == 0))
+ return -EINVAL;
+
+#if 0
+ if (!fbmon_valid_timings(pixclock, htotal, vtotal, info))
+ return -EINVAL;
+#endif
+
+ return 0;
+}
+
+static int encode_var(struct fb_var_screeninfo *var,
+ const struct atyfb_par *par)
+{
+ memset(var, 0, sizeof(struct fb_var_screeninfo));
+
+ var->xres = vmode_attrs[par->vmode-1].hres;
+ var->yres = vmode_attrs[par->vmode-1].vres;
+ var->xres_virtual = par->vxres;
+ var->yres_virtual = par->vyres;
+ var->xoffset = par->xoffset;
+ var->yoffset = par->yoffset;
+ var->grayscale = 0;
+ switch (par->cmode) {
+ case CMODE_8:
+ var->bits_per_pixel = 8;
+ var->red.offset = 0;
+ var->red.length = 8;
+ var->green.offset = 0;
+ var->green.length = 8;
+ var->blue.offset = 0;
+ var->blue.length = 8;
+ var->transp.offset = 0;
+ var->transp.length = 0;
+ break;
+ case CMODE_16: /* RGB 555 */
+ var->bits_per_pixel = 16;
+ var->red.offset = 10;
+ var->red.length = 5;
+ var->green.offset = 5;
+ var->green.length = 5;
+ var->blue.offset = 0;
+ var->blue.length = 5;
+ var->transp.offset = 0;
+ var->transp.length = 0;
+ break;
+ case CMODE_32: /* RGB 888 */
+ var->bits_per_pixel = 32;
+ var->red.offset = 16;
+ var->red.length = 8;
+ var->green.offset = 8;
+ var->green.length = 8;
+ var->blue.offset = 0;
+ var->blue.length = 8;
+ var->transp.offset = 24;
+ var->transp.length = 8;
+ break;
+ }
+ var->red.msb_right = 0;
+ var->green.msb_right = 0;
+ var->blue.msb_right = 0;
+ var->transp.msb_right = 0;
+ var->nonstd = 0;
+ var->activate = 0;
+ var->height = -1;
+ var->width = -1;
+ var->accel = /* FB_ACCEL_ATY */ 0;
+ var->vmode = FB_VMODE_NONINTERLACED;
+ var->left_margin = var->right_margin = 64; /* guesses */
+ var->upper_margin = var->lower_margin = 32;
+ var->hsync_len = 64;
+ var->vsync_len = 2;
+
+ /* no long long support in the kernel :-( */
+ /* this splittig trick will work if xres > 232 */
+ var->pixclock = 1000000000/
+ (var->left_margin+var->xres+var->right_margin+var->hsync_len);
+ var->pixclock *= 1000;
+ var->pixclock /= vmode_attrs[par->vmode-1].vfreq*
+ (var->upper_margin+var->yres+var->lower_margin+var->vsync_len);
+ var->sync = 0;
+
+ return 0;
+}
+
+
+static void init_par(struct atyfb_par *par, int vmode, int cmode)
+{
+ par->vmode = vmode;
+ par->cmode = cmode;
+ par->vxres = vmode_attrs[vmode-1].hres;
+ par->vyres = vmode_attrs[vmode-1].vres;
+ par->xoffset = 0;
+ par->yoffset = 0;
+}
+
+
+ /*
+ * Get the Fixed Part of the Display
+ */
+
+static int atyfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
+{
+ struct atyfb_par par;
+
+ if (con == -1)
+ par = default_par;
+ else
+ decode_var(&fb_display[con].var, &par);
+ encode_fix(fix, &par);
+ return 0;
+}
+
+
+ /*
+ * Get the User Defined Part of the Display
+ */
+
+static int atyfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ if (con == -1)
+ encode_var(var, &default_par);
+ else
+ *var=fb_display[con].var;
+ return 0;
+}
+
+
+ /*
+ * Set the User Defined Part of the Display
+ */
+
+static int atyfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ struct atyfb_par par;
+ struct display *display;
+ int oldxres, oldyres, oldvxres, oldvyres, oldbpp;
+ int err;
+ int activate = var->activate;
+
+ if (con >= 0)
+ display = &fb_display[con];
+ else
+ display = &fb_disp; /* used during initialization */
+
+ if ((err = decode_var(var, &par)))
+ return err;
+
+ encode_var(var, &par);
+
+ if ((activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) {
+ oldxres = display->var.xres;
+ oldyres = display->var.yres;
+ oldvxres = display->var.xres_virtual;
+ oldvyres = display->var.yres_virtual;
+ oldbpp = display->var.bits_per_pixel;
+ display->var = *var;
+ if (oldxres != var->xres || oldyres != var->yres ||
+ oldvxres != var->xres_virtual || oldvyres != var->yres_virtual ||
+ oldbpp != var->bits_per_pixel) {
+ struct fb_fix_screeninfo fix;
+
+ encode_fix(&fix, &par);
+ display->screen_base = (u_char *)fix.smem_start;
+ display->visual = fix.visual;
+ display->type = fix.type;
+ display->type_aux = fix.type_aux;
+ display->ypanstep = fix.ypanstep;
+ display->ywrapstep = fix.ywrapstep;
+ display->line_length = fix.line_length;
+ display->can_soft_blank = 1;
+ display->inverse = 0;
+ switch (par.cmode) {
+ case CMODE_8:
+#if 1
+ display->dispsw = &fbcon_cfb8;
+#else
+ display->dispsw = &fbcon_aty8;
+#endif
+ break;
+ case CMODE_16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+ case CMODE_32:
+ display->dispsw = &fbcon_cfb32;
+ break;
+ default:
+ display->dispsw = NULL;
+ break;
+ }
+ if (fb_info.changevar)
+ (*fb_info.changevar)(con);
+ }
+ if (con == currcon)
+ atyfb_set_par(&par);
+ if (oldbpp != var->bits_per_pixel) {
+ if ((err = fb_alloc_cmap(&display->cmap, 0, 0)))
+ return err;
+ do_install_cmap(con, info);
+ }
+ }
+
+ return 0;
+}
+
+
+ /*
+ * Pan or Wrap the Display
+ *
+ * This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
+ */
+
+static int atyfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ u32 xres, yres, xoffset, yoffset;
+ struct atyfb_par *par = &current_par;
+
+ xres = vmode_attrs[par->vmode-1].hres;
+ yres = vmode_attrs[par->vmode-1].vres;
+ xoffset = (var->xoffset+7) & ~7;
+ yoffset = var->yoffset;
+ if (xoffset+xres > par->vxres || yoffset+yres > par->vyres)
+ return -EINVAL;
+ par->xoffset = xoffset;
+ par->yoffset = yoffset;
+ set_off_pitch(par);
+ return 0;
+}
+
+ /*
+ * Get the Colormap
+ */
+
+static int atyfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ if (con == currcon) /* current console? */
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, atyfb_getcolreg,
+ info);
+ else if (fb_display[con].cmap.len) /* non default colormap? */
+ fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
+ else
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ cmap, kspc ? 0 : 2);
+ return 0;
+}
+
+ /*
+ * Set the Colormap
+ */
+
+static int atyfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ int err;
+
+ if (!fb_display[con].cmap.len) { /* no colormap allocated? */
+ if ((err = fb_alloc_cmap(&fb_display[con].cmap,
+ 1<<fb_display[con].var.bits_per_pixel, 0)))
+ return err;
+ }
+ if (con == currcon) /* current console? */
+ return fb_set_cmap(cmap, &fb_display[con].var, kspc, atyfb_setcolreg,
+ info);
+ else
+ fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
+ return 0;
+}
+
+
+static int atyfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info)
+{
+ return -EINVAL;
+}
+
+
+ /*
+ * Initialisation
+ */
+
+__initfunc(unsigned long atyfb_init(unsigned long mem_start))
+{
+#ifdef __powerpc__
+ /* We don't want to be called like this. */
+ /* We rely on Open Firmware (offb) instead. */
+ return mem_start;
+#else /* !__powerpc__ */
+ /* To be merged with Bernd's mach64fb */
+ return mem_start;
+#endif /* !__powerpc__ */
+}
+
+
+unsigned long atyfb_of_init(unsigned long mem_start, struct device_node *dp)
+{
+ int i, err, sense;
+ struct fb_var_screeninfo var;
+ struct aty_regvals *init;
+ unsigned long addr;
+ unsigned char bus, devfn;
+ unsigned short cmd;
+
+ if (dp->next)
+ printk("Warning: only using first ATI card detected\n");
+ if (dp->n_addrs != 1 && dp->n_addrs != 3)
+ printk("Warning: expecting 1 or 3 addresses for ATY (got %d)",
+ dp->n_addrs);
+
+ ati_regbase = (int)ioremap((0x7ffc00 + dp->addrs[0].address), 0x1000);
+ aty_cmap_regs = (struct aty_cmap_regs *)(ati_regbase + 0xC0);
+
+ /* enable memory-space accesses using config-space command register */
+ if (pci_device_loc(dp, &bus, &devfn) == 0) {
+ pcibios_read_config_word(bus, devfn, PCI_COMMAND, &cmd);
+ if (cmd != 0xffff) {
+ cmd |= PCI_COMMAND_MEMORY;
+ pcibios_write_config_word(bus, devfn, PCI_COMMAND, cmd);
+ }
+ }
+ chip_type = (aty_ld_le32(CONFIG_CHIP_ID) & CFG_CHIP_TYPE);
+
+ i = aty_ld_le32(MEM_CNTL);
+ if (chip_type != MACH64_GT_ID)
+ switch (i & MEM_SIZE_ALIAS) {
+ case MEM_SIZE_512K:
+ total_vram = 0x80000;
+ break;
+ case MEM_SIZE_1M:
+ total_vram = 0x100000;
+ break;
+ case MEM_SIZE_2M:
+ total_vram = 0x200000;
+ break;
+ case MEM_SIZE_4M:
+ total_vram = 0x400000;
+ break;
+ case MEM_SIZE_6M:
+ total_vram = 0x600000;
+ break;
+ case MEM_SIZE_8M:
+ total_vram = 0x800000;
+ break;
+ default:
+ total_vram = 0x80000;
+ }
+ else
+ switch (i & 0xF) { /* 0xF used instead of MEM_SIZE_ALIAS */
+ case MEM_SIZE_512K:
+ total_vram = 0x80000;
+ break;
+ case MEM_SIZE_1M:
+ total_vram = 0x100000;
+ break;
+ case MEM_SIZE_2M_GTB:
+ total_vram = 0x200000;
+ break;
+ case MEM_SIZE_4M_GTB:
+ total_vram = 0x400000;
+ break;
+ case MEM_SIZE_6M_GTB:
+ total_vram = 0x600000;
+ break;
+ case MEM_SIZE_8M_GTB:
+ total_vram = 0x800000;
+ break;
+ default:
+ total_vram = 0x80000;
+ }
+
+#if 1
+ printk("aty_display_init: node = %p, addrs = ", dp->node);
+ printk(" %x(%x)", dp->addrs[0].address, dp->addrs[0].size);
+ printk(", intrs =");
+ for (i = 0; i < dp->n_intrs; ++i)
+ printk(" %x", dp->intrs[i].line);
+ printk("\nregbase: %x pci loc: %x:%x total_vram: %x cregs: %p\n",
+ (int)ati_regbase, bus, devfn, total_vram, aty_cmap_regs);
+#endif
+
+ /* Map in frame buffer */
+ addr = dp->addrs[0].address;
+
+ /* use the big-endian aperture (??) */
+ addr += 0x800000;
+ frame_buffer = (unsigned long)__ioremap(addr, 0x800000, _PAGE_WRITETHRU);
+
+ if (default_video_mode != -1) {
+ sense = read_aty_sense();
+ printk("monitor sense = %x\n", sense);
+ if (default_video_mode == VMODE_NVRAM) {
+ default_video_mode = nvram_read_byte(NV_VMODE);
+ init = get_aty_struct(default_video_mode);
+ if (default_video_mode <= 0 ||
+ default_video_mode > VMODE_MAX || init == 0)
+ default_video_mode = VMODE_CHOOSE;
+ }
+ if (default_video_mode == VMODE_CHOOSE)
+ default_video_mode = map_monitor_sense(sense);
+
+ init = get_aty_struct(default_video_mode);
+ if (!init)
+ default_video_mode = VMODE_640_480_60;
+ }
+
+ /*
+ * Reduce the pixel size if we don't have enough VRAM.
+ */
+
+ if (default_color_mode == CMODE_NVRAM)
+ default_color_mode = nvram_read_byte(NV_CMODE);
+ if (default_color_mode < CMODE_8 ||
+ default_color_mode > CMODE_32)
+ default_color_mode = CMODE_8;
+
+ init_par(&default_par, default_video_mode, default_color_mode);
+ while (aty_vram_reqd(&default_par) > total_vram) {
+ while (default_color_mode > CMODE_8 &&
+ aty_vram_reqd(&default_par) > total_vram) {
+ --default_color_mode;
+ init_par(&default_par, default_video_mode, default_color_mode);
+ }
+ /*
+ * adjust the video mode smaller if there still is not enough VRAM
+ */
+ if (aty_vram_reqd(&default_par) > total_vram)
+ do {
+ default_video_mode--;
+ init_par(&default_par, default_video_mode, default_color_mode);
+ init = get_aty_struct(default_video_mode);
+ } while ((init == 0) &&
+ (default_video_mode > VMODE_640_480_60));
+ }
+
+ if (chip_type == MACH64_GT_ID && (aty_ld_le32(CONFIG_STAT0) & 7) == 5
+ && init->crtc_gen_cntl[1] == 0) {
+ default_video_mode = VMODE_640_480_67;
+ default_color_mode = CMODE_8;
+ init_par(&default_par, default_video_mode, default_color_mode);
+ }
+
+ switch (chip_type) {
+ case MACH64_GX_ID:
+ strcat(atyfb_name, "GX");
+ break;
+ case MACH64_VT_ID:
+ strcat(atyfb_name, "VT");
+ break;
+ case MACH64_GT_ID:
+ strcat(atyfb_name, "GT");
+ break;
+ default:
+ break;
+ }
+ strcpy(fb_info.modename, atyfb_name);
+ fb_info.node = -1;
+ fb_info.fbops = &atyfb_ops;
+ fb_info.disp = &fb_disp;
+ fb_info.fontname[0] = '\0';
+ fb_info.changevar = NULL;
+ fb_info.switch_con = &atyfbcon_switch;
+ fb_info.updatevar = &atyfbcon_updatevar;
+ fb_info.blank = &atyfbcon_blank;
+
+ err = register_framebuffer(&fb_info);
+ if (err < 0)
+ return mem_start;
+
+ for (i = 0; i < 16; i++) {
+ int j = color_table[i];
+ palette[i].red = default_red[j];
+ palette[i].green = default_grn[j];
+ palette[i].blue = default_blu[j];
+ }
+ atyfb_set_par(&default_par);
+ encode_var(&var, &default_par);
+ atyfb_set_var(&var, -1, &fb_info);
+
+ printk("fb%d: %s frame buffer device on %s\n", GET_FB_IDX(fb_info.node),
+ atyfb_name, dp->full_name);
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+ if (!console_fb_info) {
+ console_fb_info = &fb_info;
+ console_setmode_ptr = atyfb_console_setmode;
+ console_set_cmap_ptr = atyfb_set_cmap;
+ }
+#endif /* CONFIG_FB_COMPAT_XPMAC) */
+
+ return mem_start;
+}
+
+
+/* XXX: doesn't work yet */
+void atyfb_setup(char *options, int *ints)
+{
+ char *this_opt;
+ int vmode;
+ int depth;
+
+ if (!options || !*options)
+ return;
+
+ for (this_opt = strtok(options, ","); this_opt;
+ this_opt = strtok(NULL, ",")) {
+ if (!strncmp(this_opt, "vmode:", 6)) {
+ vmode = simple_strtoul(this_opt+6, NULL, 0);
+ if (vmode > 0 && vmode <= VMODE_MAX)
+ default_video_mode = vmode;
+ } else if (!strncmp(this_opt, "cmode:", 6)) {
+ depth = simple_strtoul(this_opt+6, NULL, 0);
+ switch (depth) {
+ case 8:
+ default_color_mode = CMODE_8;
+ break;
+ case 15:
+ case 16:
+ default_color_mode = CMODE_16;
+ break;
+ case 24:
+ case 32:
+ default_color_mode = CMODE_32;
+ break;
+ };
+ }
+ }
+}
+
+
+static int atyfbcon_switch(int con, struct fb_info *info)
+{
+ struct atyfb_par par;
+
+ /* Do we have to save the colormap? */
+ if (fb_display[currcon].cmap.len)
+ fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
+ atyfb_getcolreg, info);
+ currcon = con;
+ decode_var(&fb_display[con].var, &par);
+ atyfb_set_par(&par);
+ /* Install new colormap */
+ do_install_cmap(con, info);
+ return 0;
+}
+
+ /*
+ * Update the `var' structure (called by fbcon.c)
+ */
+
+static int atyfbcon_updatevar(int con, struct fb_info *info)
+{
+ current_par.yoffset = fb_display[con].var.yoffset;
+ set_off_pitch(&current_par);
+ return 0;
+}
+
+ /*
+ * Blank the display.
+ */
+
+static void atyfbcon_blank(int blank, struct fb_info *info)
+{
+ char gen_cntl;
+
+ gen_cntl = aty_ld_8(CRTC_GEN_CNTL);
+ if (blank & VESA_VSYNC_SUSPEND)
+ gen_cntl |= 0x8;
+ if (blank & VESA_HSYNC_SUSPEND)
+ gen_cntl |= 0x4;
+ if ((blank & VESA_POWERDOWN) == VESA_POWERDOWN)
+ gen_cntl |= 0x40;
+ if (blank == VESA_NO_BLANKING)
+ gen_cntl &= ~(0x4c);
+ aty_st_8(CRTC_GEN_CNTL, gen_cntl);
+}
+
+
+ /*
+ * Read a single color register and split it into
+ * colors/transparent. Return != 0 for invalid regno.
+ */
+
+static int atyfb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info)
+{
+ if (regno > 255)
+ return 1;
+ *red = palette[regno].red;
+ *green = palette[regno].green;
+ *blue = palette[regno].blue;
+ return 0;
+}
+
+
+ /*
+ * Set a single color register. The values supplied are already
+ * rounded down to the hardware's capabilities (according to the
+ * entries in the var structure). Return != 0 for invalid regno.
+ */
+
+static int atyfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info)
+{
+ int i, scale;
+
+ if (regno > 255)
+ return 1;
+ palette[regno].red = red;
+ palette[regno].green = green;
+ palette[regno].blue = blue;
+ aty_WaitQueue(2);
+ i = aty_ld_8(DAC_CNTL) & 0xfc;
+ if (chip_type == MACH64_GT_ID)
+ i |= 0x2; /*DAC_CNTL|0x2 turns off the extra brightness for gt*/
+ aty_st_8(DAC_CNTL, i);
+ aty_st_8(DAC_REGS + DAC_MASK, 0xff);
+ eieio();
+ scale = ((chip_type != MACH64_GX_ID) &&
+ (current_par.cmode == CMODE_16)) ? 3 : 0;
+ aty_WaitQueue(4);
+ aty_cmap_regs->windex = regno << scale;
+ eieio();
+ aty_cmap_regs->lut = red << scale;
+ eieio();
+ aty_cmap_regs->lut = green << scale;
+ eieio();
+ aty_cmap_regs->lut = blue << scale;
+ eieio();
+ if (regno < 16) {
+#ifdef CONFIG_FBCON_CFB16
+ fbcon_cfb16_cmap[regno] = (regno << 10) | (regno << 5) | regno;
+#endif
+#ifdef CONFIG_FBCON_CFB32
+ fbcon_cfb32_cmap[regno] = (regno << 24) | (regno << 16) |
+ (regno << 8) | regno;
+#endif
+ }
+ return 0;
+}
+
+
+static void do_install_cmap(int con, struct fb_info *info)
+{
+ if (con != currcon)
+ return;
+ if (fb_display[con].cmap.len)
+ fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
+ atyfb_setcolreg, info);
+ else
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, atyfb_setcolreg,
+ info);
+}
+
+
+ /*
+ * Accelerated functions
+ */
+
+void aty_waitblit(void)
+{
+ aty_WaitIdleEmpty(); /* Make sure that all commands have finished */
+}
+
+void aty_rectcopy(int srcx, int srcy, int dstx, int dsty, u_int width,
+ u_int height)
+{
+ u_int direction = 0;
+
+ if (srcy < dsty) {
+ dsty += height - 1;
+ srcy += height - 1;
+ } else
+ direction |= DST_Y_TOP_TO_BOTTOM;
+
+ if (srcx < dstx) {
+ dstx += width - 1;
+ srcx += width - 1;
+ } else
+ direction |= DST_X_LEFT_TO_RIGHT;
+
+ aty_WaitQueue(4);
+ aty_st_le32(DP_WRITE_MSK, 0x000000FF /* pGC->planemask */ );
+ aty_st_le32(DP_MIX, (MIX_SRC << 16) | MIX_DST);
+ aty_st_le32(DP_SRC, FRGD_SRC_BLIT);
+
+ aty_WaitQueue(5);
+ aty_st_le32(SRC_Y_X, (srcx << 16) | (srcy & 0x0000ffff));
+ aty_st_le32(SRC_WIDTH1, width);
+ aty_st_le32(DST_CNTL, direction);
+ aty_st_le32(DST_Y_X, (dstx << 16) | (dsty & 0x0000ffff));
+ aty_st_le32(DST_HEIGHT_WIDTH, (width << 16) | (height & 0x0000ffff));
+
+ aty_WaitIdleEmpty(); /* Make sure that all commands have finished */
+
+ /*
+ * Make sure that the destination trajectory is correctly set
+ * for subsequent calls. MACH64_BIT_BLT is the only function that
+ * currently changes the destination trajectory from L->R and T->B.
+ */
+ aty_st_le32(DST_CNTL, (DST_X_LEFT_TO_RIGHT | DST_Y_TOP_TO_BOTTOM));
+}
+
+void aty_rectfill(int dstx, int dsty, u_int width, u_int height, u_int color)
+{
+ if (!width || !height)
+ return;
+
+ aty_WaitQueue(5);
+ aty_st_le32(DP_FRGD_CLR, color /* pGC->fgPixel */ );
+ aty_st_le32(DP_WRITE_MSK, 0x000000FF /* pGC->planemask */ );
+ aty_st_le32(DP_MIX, (MIX_SRC << 16) | MIX_DST);
+ aty_st_le32(DP_SRC, FRGD_SRC_FRGD_CLR);
+
+ aty_st_le32(DST_CNTL, DST_X_LEFT_TO_RIGHT | DST_Y_TOP_TO_BOTTOM);
+
+ aty_WaitQueue(2);
+ aty_st_le32(DST_Y_X, (((u_int)dstx << 16) | ((u_int)dsty & 0x0000ffff)));
+ aty_st_le32(DST_HEIGHT_WIDTH, (((u_int)width << 16) | height));
+
+ aty_WaitIdleEmpty(); /* Make sure that all commands have finished */
+}
+
+
+ /*
+ * Text console acceleration
+ */
+
+static void fbcon_aty8_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ sx *= p->fontwidth;
+ sy *= p->fontheight;
+ dx *= p->fontwidth;
+ dy *= p->fontheight;
+ width *= p->fontwidth;
+ height *= p->fontheight;
+
+ aty_rectcopy(sx, sy, dx, dy, width, height);
+}
+
+static void fbcon_aty8_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
+{
+ u32 bgx = attr_bgcol_ec(p, conp);
+ bgx |= (bgx << 8);
+ bgx |= (bgx << 16);
+
+ sx *= p->fontwidth;
+ sy *= p->fontheight;
+ width *= p->fontwidth;
+ height *= p->fontheight;
+
+ aty_rectfill(sx, sy, width, height, bgx);
+}
+
+static void fbcon_aty8_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx)
+{
+ aty_waitblit();
+ fbcon_cfb8_putc(conp, p, c, yy, xx);
+}
+
+static void fbcon_aty8_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx)
+{
+ aty_waitblit();
+ fbcon_cfb8_putcs(conp, p, s, count, yy, xx);
+}
+
+static struct display_switch fbcon_aty8 = {
+ fbcon_cfb8_setup, fbcon_aty8_bmove, fbcon_aty8_clear, fbcon_aty8_putc,
+ fbcon_aty8_putcs, fbcon_cfb8_revc
+};
+
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+
+ /*
+ * Backward compatibility mode for Xpmac
+ */
+
+static int atyfb_console_setmode(struct vc_mode *mode, int doit)
+{
+ int err;
+ struct fb_var_screeninfo var;
+ struct atyfb_par par;
+ int vmode, cmode;
+
+ if (mode->mode <= 0 || mode->mode > VMODE_MAX )
+ return -EINVAL;
+ vmode = mode->mode;
+
+ switch (mode->depth) {
+ case 24:
+ case 32:
+ cmode = CMODE_32;
+ break;
+ case 16:
+ cmode = CMODE_16;
+ break;
+ case 8:
+ case 0: /* (default) */
+ cmode = CMODE_8;
+ break;
+ default:
+ return -EINVAL;
+ }
+ init_par(&par, vmode, cmode);
+ encode_var(&var, &par);
+ if ((err = decode_var(&var, &par)))
+ return err;
+ if (doit)
+ atyfb_set_var(&var, currcon, 0);
+ return 0;
+}
+
+#endif /* CONFIG_FB_COMPAT_XPMAC */
diff --git a/drivers/video/cyberfb.c b/drivers/video/cyberfb.c
index ccd83bb01..2eaacb57d 100644
--- a/drivers/video/cyberfb.c
+++ b/drivers/video/cyberfb.c
@@ -36,18 +36,34 @@
#include <asm/system.h>
#include <asm/irq.h>
#include <asm/pgtable.h>
+#include <asm/amigahw.h>
+
#include "s3blit.h"
+#include "fbcon.h"
+#include "fbcon-cfb8.h"
+#include "fbcon-cfb16.h"
+
+#ifdef CYBERFBDEBUG
+#define DPRINTK(fmt, args...) printk(KERN_DEBUG "%s: " fmt, __FUNCTION__ , ## args)
+#else
+#define DPRINTK(fmt, args...)
+#endif
#define arraysize(x) (sizeof(x)/sizeof(*(x)))
-struct Cyber_fb_par {
+
+#define wb_64(reg,dat) (*((unsigned char volatile *)CyberRegs + reg) = dat)
+
+
+
+struct cyberfb_par {
int xres;
int yres;
int bpp;
};
-static struct Cyber_fb_par current_par;
+static struct cyberfb_par current_par;
static int current_par_valid = 0;
static int currcon = 0;
@@ -68,13 +84,13 @@ static struct fb_hwswitch {
/* Display Control */
- int (*encode_fix)(struct fb_fix_screeninfo *fix, struct Cyber_fb_par *par);
- int (*decode_var)(struct fb_var_screeninfo *var, struct Cyber_fb_par *par);
- int (*encode_var)(struct fb_var_screeninfo *var, struct Cyber_fb_par *par);
+ int (*encode_fix)(struct fb_fix_screeninfo *fix, struct cyberfb_par *par);
+ int (*decode_var)(struct fb_var_screeninfo *var, struct cyberfb_par *par);
+ int (*encode_var)(struct fb_var_screeninfo *var, struct cyberfb_par *par);
int (*getcolreg)(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp);
+ u_int *transp, struct fb_info *info);
int (*setcolreg)(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp);
+ u_int transp, struct fb_info *info);
void (*blank)(int blank);
} *fbhw;
@@ -83,7 +99,7 @@ static struct fb_hwswitch {
* Frame Buffer Name
*/
-static char Cyber_fb_name[16] = "Cybervision";
+static char cyberfb_name[16] = "Cybervision";
/*
@@ -106,105 +122,67 @@ static unsigned char Cyber_colour_table [256][4];
static unsigned long CyberMem;
static unsigned long CyberSize;
static volatile char *CyberRegs;
-
-
-/*
- * Predefined Video Mode Names
- */
-
-static char *Cyber_fb_modenames[] = {
-
- /*
- * Autodetect (Default) Video Mode
- */
-
- "default",
-
- /*
- * Predefined Video Modes
- */
-
- "cyber8", /* Cybervision 8 bpp */
- "cyber16", /* Cybervision 16 bpp */
- "800x600x8",
- "640x480x8",
-
- /*
- * Dummy Video Modes
- */
-
- "dummy", "dummy", "dummy", "dummy", "dummy", "dummy", "dummy", "dummy",
- "dummy", "dummy", "dummy", "dummy", "dummy", "dummy", "dummy", "dummy",
- "dummy", "dummy",
-
- /*
- * User Defined Video Modes
- *
- * This doesn't work yet!!
- */
-
- "user0", "user1", "user2", "user3", "user4", "user5", "user6", "user7"
-};
-
+
/*
- * Predefined Video Mode Definitions
+ * Predefined Video Modes
*/
-static struct fb_var_screeninfo cyber_fb_predefined[] = {
-
- /*
- * Autodetect (Default) Video Mode
- */
-
- { 0, },
-
- /*
- * Predefined Video Modes
- */
-
- {
- /* Cybervision 8 bpp */
- CYBER8_WIDTH, CYBER8_HEIGHT, CYBER8_WIDTH, CYBER8_HEIGHT, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
- FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- }, {
- /* Cybervision 16 bpp */
- 800, 600, 800, 600, 0, 0, 16, 0,
- {11, 5, 0}, {5, 6, 0}, {0, 5, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, CYBER16_PIXCLOCK, 64, 96, 35, 12, 112, 2,
- FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- }, {
- /* Cybervision 8 bpp */
- 800, 600, 800, 600, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
- FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- }, {
- /* Cybervision 8 bpp */
- 640, 480, 640, 480, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
- FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- },
- /*
- * Dummy Video Modes
- */
-
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, },
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, },
-
- /*
- * User Defined Video Modes
- */
-
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }
+static struct fb_videomode cyberfb_predefined[] __initdata = {
+ {
+ "640x480-8", { /* Cybervision 8 bpp */
+ 640, 480, 640, 480, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "800x600-8", { /* Cybervision 8 bpp */
+ 800, 600, 800, 600, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1024x768-8", { /* Cybervision 8 bpp */
+ 1024, 768, 1024, 768, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1152x886-8", { /* Cybervision 8 bpp */
+ 1152, 886, 1152, 886, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1280x1024-8", { /* Cybervision 8 bpp */
+ 1280, 1024, 1280, 1024, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1600x1200-8", { /* Cybervision 8 bpp */
+ 1600, 1200, 1600, 1200, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "800x600-16", { /* Cybervision 16 bpp */
+ 800, 600, 800, 600, 0, 0, 16, 0,
+ {11, 5, 0}, {5, 6, 0}, {0, 5, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, CYBER16_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }
};
-#define NUM_TOTAL_MODES arraysize(cyber_fb_predefined)
-#define NUM_PREDEF_MODES (5)
+#define NUM_TOTAL_MODES arraysize(cyberfb_predefined)
static int Cyberfb_inverse = 0;
@@ -212,57 +190,72 @@ static int Cyberfb_inverse = 0;
static int Cyberfb_Cyber8 = 0; /* Use Cybervision board */
static int Cyberfb_Cyber16 = 0; /* Use Cybervision board */
#endif
-static int Cyberfb_mode = 0;
-
/*
* Some default modes
*/
-#define CYBER8_DEFMODE (1)
-#define CYBER16_DEFMODE (2)
+#define CYBER8_DEFMODE (0)
+#define CYBER16_DEFMODE (6)
+
+static struct fb_var_screeninfo cyberfb_default;
/*
* Interface used by the world
*/
-void Cyber_video_setup(char *options, int *ints);
-
-static int Cyber_fb_open(int fbidx);
-static int Cyber_fb_release(int fbidx);
-static int Cyber_fb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int Cyber_fb_get_var(struct fb_var_screeninfo *var, int con);
-static int Cyber_fb_set_var(struct fb_var_screeninfo *var, int con);
-static int Cyber_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int Cyber_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int Cyber_fb_pan_display(struct fb_var_screeninfo *var, int con);
-static int Cyber_fb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con);
+void cyberfb_setup(char *options, int *ints);
+
+static int cyberfb_open(struct fb_info *info);
+static int cyberfb_release(struct fb_info *info);
+static int cyberfb_get_fix(struct fb_fix_screeninfo *fix, int con, struct
+fb_info *info);
+static int cyberfb_get_var(struct fb_var_screeninfo *var, int con, struct
+fb_info *info);
+static int cyberfb_set_var(struct fb_var_screeninfo *var, int con, struct
+fb_info *info);
+static int cyberfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int cyberfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int cyberfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int cyberfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info);
/*
* Interface to the low level console driver
*/
-unsigned long Cyber_fb_init(unsigned long mem_start);
-static int Cyberfb_switch(int con);
-static int Cyberfb_updatevar(int con);
-static void Cyberfb_blank(int blank);
-static int Cyberfb_setcmap(struct fb_cmap *cmap, int con);
+unsigned long cyberfb_init(unsigned long mem_start);
+static int Cyberfb_switch(int con, struct fb_info *info);
+static int Cyberfb_updatevar(int con, struct fb_info *info);
+static void Cyberfb_blank(int blank, struct fb_info *info);
+
+
+/*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static struct display_switch fbcon_cyber8;
+#endif
/*
* Accelerated Functions used by the low level console driver
*/
-void Cyber_WaitQueue(u_short fifo);
-void Cyber_WaitBlit(void);
-void Cyber_BitBLT(u_short curx, u_short cury, u_short destx, u_short desty,
- u_short width, u_short height, u_short mode);
-void Cyber_RectFill(u_short x, u_short y, u_short width, u_short height,
- u_short mode, u_short color);
-void Cyber_MoveCursor(u_short x, u_short y);
+static void Cyber_WaitQueue(u_short fifo);
+static void Cyber_WaitBlit(void);
+static void Cyber_BitBLT(u_short curx, u_short cury, u_short destx,
+ u_short desty, u_short width, u_short height,
+ u_short mode);
+static void Cyber_RectFill(u_short x, u_short y, u_short width, u_short height,
+ u_short mode, u_short color);
+static void Cyber_MoveCursor(u_short x, u_short y);
/*
@@ -271,15 +264,15 @@ void Cyber_MoveCursor(u_short x, u_short y);
static int Cyber_init(void);
static int Cyber_encode_fix(struct fb_fix_screeninfo *fix,
- struct Cyber_fb_par *par);
+ struct cyberfb_par *par);
static int Cyber_decode_var(struct fb_var_screeninfo *var,
- struct Cyber_fb_par *par);
+ struct cyberfb_par *par);
static int Cyber_encode_var(struct fb_var_screeninfo *var,
- struct Cyber_fb_par *par);
+ struct cyberfb_par *par);
static int Cyber_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp);
+ u_int *transp, struct fb_info *info);
static int Cyber_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp);
+ u_int transp, struct fb_info *info);
static void Cyber_blank(int blank);
@@ -287,11 +280,11 @@ static void Cyber_blank(int blank);
* Internal routines
*/
-static void Cyber_fb_get_par(struct Cyber_fb_par *par);
-static void Cyber_fb_set_par(struct Cyber_fb_par *par);
+static void cyberfb_get_par(struct cyberfb_par *par);
+static void cyberfb_set_par(struct cyberfb_par *par);
static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive);
-static void do_install_cmap(int con);
-static void Cyber_fb_set_disp(int con);
+static void do_install_cmap(int con, struct fb_info *info);
+static void cyberfb_set_disp(int con, struct fb_info *info);
static int get_video_mode(const char *name);
@@ -311,41 +304,32 @@ static int Cyber_init(void)
char size;
volatile u_long *CursorBase;
-#if 0
- if (Cyberfb_mode == -1)
+ for (i = 0; i < 256; i++)
{
- if (Cyberfb_Cyber8)
- Cyberfb_mode = CYBER8_DEFMODE;
- else
- Cyberfb_mode = CYBER16_DEFMODE;
+ Cyber_colour_table [i][0] = i;
+ Cyber_colour_table [i][1] = i;
+ Cyber_colour_table [i][2] = i;
+ Cyber_colour_table [i][3] = 0;
}
-#endif
-
- for (i = 0; i < 256; i++)
-
- for (i = 0; i < 256; i++)
- {
- Cyber_colour_table [i][0] = i;
- Cyber_colour_table [i][1] = i;
- Cyber_colour_table [i][2] = i;
- Cyber_colour_table [i][3] = 0;
- }
/*
* Just clear the thing for the biggest mode.
+ *
+ * ++Andre, TODO: determine size first, then clear all memory
+ * (the 3D penguin might need texture memory :-) )
*/
- memset ((char*)CyberMem, 0, CYBER8_WIDTH * CYBER8_HEIGHT);
+ memset ((char*)CyberMem, 0, 1600 * 1200);
/* Disable hardware cursor */
- *(CyberRegs + S3_CRTC_ADR) = S3_REG_LOCK2;
- *(CyberRegs + S3_CRTC_DATA) = 0xa0;
- *(CyberRegs + S3_CRTC_ADR) = S3_HGC_MODE;
- *(CyberRegs + S3_CRTC_DATA) = 0x00;
- *(CyberRegs + S3_CRTC_ADR) = S3_HWGC_DX;
- *(CyberRegs + S3_CRTC_DATA) = 0x00;
- *(CyberRegs + S3_CRTC_ADR) = S3_HWGC_DY;
- *(CyberRegs + S3_CRTC_DATA) = 0x00;
+ wb_64(S3_CRTC_ADR, S3_REG_LOCK2);
+ wb_64(S3_CRTC_DATA, 0xa0);
+ wb_64(S3_CRTC_ADR, S3_HGC_MODE);
+ wb_64(S3_CRTC_DATA, 0x00);
+ wb_64(S3_CRTC_ADR, S3_HWGC_DX);
+ wb_64(S3_CRTC_DATA, 0x00);
+ wb_64(S3_CRTC_ADR, S3_HWGC_DY);
+ wb_64(S3_CRTC_DATA, 0x00);
/* Get memory size (if not 2MB it is 4MB) */
*(CyberRegs + S3_CRTC_ADR) = S3_LAW_CTL;
@@ -372,8 +356,8 @@ static int Cyber_init(void)
*(CursorBase+3+(i*4)) = 0xffff0000;
}
- Cyber_setcolreg (255, 56, 100, 160, 0);
- Cyber_setcolreg (254, 0, 0, 0, 0);
+ Cyber_setcolreg (255, 56, 100, 160, 0, NULL /* unused */);
+ Cyber_setcolreg (254, 0, 0, 0, 0, NULL /* unused */);
return 0;
}
@@ -385,11 +369,11 @@ static int Cyber_init(void)
*/
static int Cyber_encode_fix(struct fb_fix_screeninfo *fix,
- struct Cyber_fb_par *par)
+ struct cyberfb_par *par)
{
int i;
- strcpy(fix->id, Cyber_fb_name);
+ strcpy(fix->id, cyberfb_name);
fix->smem_start = (caddr_t)CyberMem;
fix->smem_len = CyberSize;
fix->mmio_start = (unsigned char *)CyberRegs;
@@ -420,7 +404,7 @@ static int Cyber_encode_fix(struct fb_fix_screeninfo *fix,
*/
static int Cyber_decode_var(struct fb_var_screeninfo *var,
- struct Cyber_fb_par *par)
+ struct cyberfb_par *par)
{
#if 1
par->xres = var->xres;
@@ -447,7 +431,7 @@ static int Cyber_decode_var(struct fb_var_screeninfo *var,
*/
static int Cyber_encode_var(struct fb_var_screeninfo *var,
- struct Cyber_fb_par *par)
+ struct cyberfb_par *par)
{
int i;
@@ -486,7 +470,10 @@ static int Cyber_encode_var(struct fb_var_screeninfo *var,
var->height = -1;
var->width = -1;
+
var->accel = FB_ACCEL_CYBERVISION;
+ DPRINTK("accel CV64\n");
+
var->vmode = FB_VMODE_NONINTERLACED;
/* Dummy values */
@@ -517,20 +504,22 @@ static int Cyber_encode_var(struct fb_var_screeninfo *var,
*/
static int Cyber_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp)
+ u_int transp, struct fb_info *info)
{
if (regno > 255)
+ {
return (1);
+ }
- *(CyberRegs + 0x3c8) = (char)regno;
+ wb_64(0x3c8, (unsigned char) regno);
Cyber_colour_table [regno][0] = red & 0xff;
Cyber_colour_table [regno][1] = green & 0xff;
Cyber_colour_table [regno][2] = blue & 0xff;
Cyber_colour_table [regno][3] = transp;
- *(CyberRegs + 0x3c9) = (red & 0xff) >> 2;
- *(CyberRegs + 0x3c9) = (green & 0xff) >> 2;
- *(CyberRegs + 0x3c9) = (blue & 0xff) >> 2;
+ wb_64(0x3c9, (red & 0xff) >> 2);
+ wb_64(0x3c9, (green & 0xff) >> 2);
+ wb_64(0x3c9, (blue & 0xff) >> 2);
return (0);
}
@@ -542,13 +531,13 @@ static int Cyber_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
*/
static int Cyber_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp)
+ u_int *transp, struct fb_info *info)
{
if (regno >= 256)
return (1);
- *red = Cyber_colour_table [regno][0];
- *green = Cyber_colour_table [regno][1];
- *blue = Cyber_colour_table [regno][2];
+ *red = Cyber_colour_table [regno][0];
+ *green = Cyber_colour_table [regno][1];
+ *blue = Cyber_colour_table [regno][2];
*transp = Cyber_colour_table [regno][3];
return (0);
}
@@ -563,28 +552,32 @@ void Cyber_blank(int blank)
int i;
if (blank)
+ {
for (i = 0; i < 256; i++)
{
- *(CyberRegs + 0x3c8) = i;
- *(CyberRegs + 0x3c9) = 0;
- *(CyberRegs + 0x3c9) = 0;
- *(CyberRegs + 0x3c9) = 0;
+ wb_64(0x3c8, (unsigned char) i);
+ wb_64(0x3c9, 0);
+ wb_64(0x3c9, 0);
+ wb_64(0x3c9, 0);
}
+ }
else
+ {
for (i = 0; i < 256; i++)
{
- *(CyberRegs + 0x3c8) = i;
- *(CyberRegs + 0x3c9) = Cyber_colour_table [i][0] >> 2;
- *(CyberRegs + 0x3c9) = Cyber_colour_table [i][1] >> 2;
- *(CyberRegs + 0x3c9) = Cyber_colour_table [i][2] >> 2;
+ wb_64(0x3c8, (unsigned char) i);
+ wb_64(0x3c9, Cyber_colour_table[i][0] >> 2);
+ wb_64(0x3c9, Cyber_colour_table[i][1] >> 2);
+ wb_64(0x3c9, Cyber_colour_table[i][2] >> 2);
}
+ }
}
/**************************************************************
* We are waiting for "fifo" FIFO-slots empty
*/
-void Cyber_WaitQueue (u_short fifo)
+static void Cyber_WaitQueue (u_short fifo)
{
u_short status;
@@ -598,7 +591,7 @@ void Cyber_WaitQueue (u_short fifo)
/**************************************************************
* We are waiting for Hardware (Graphics Engine) not busy
*/
-void Cyber_WaitBlit (void)
+static void Cyber_WaitBlit (void)
{
u_short status;
@@ -612,8 +605,9 @@ void Cyber_WaitBlit (void)
/**************************************************************
* BitBLT - Through the Plane
*/
-void Cyber_BitBLT (u_short curx, u_short cury, u_short destx, u_short desty,
- u_short width, u_short height, u_short mode)
+static void Cyber_BitBLT (u_short curx, u_short cury, u_short destx,
+ u_short desty, u_short width, u_short height,
+ u_short mode)
{
u_short blitcmd = S3_BITBLT;
@@ -655,8 +649,8 @@ void Cyber_BitBLT (u_short curx, u_short cury, u_short destx, u_short desty,
/**************************************************************
* Rectangle Fill Solid
*/
-void Cyber_RectFill (u_short x, u_short y, u_short width, u_short height,
- u_short mode, u_short color)
+static void Cyber_RectFill (u_short x, u_short y, u_short width,
+ u_short height, u_short mode, u_short color)
{
u_short blitcmd = S3_FILLEDRECT;
@@ -677,11 +671,10 @@ void Cyber_RectFill (u_short x, u_short y, u_short width, u_short height,
*((u_short volatile *)(CyberRegs + S3_CMD)) = blitcmd;
}
-
/**************************************************************
* Move cursor to x, y
*/
-void Cyber_MoveCursor (u_short x, u_short y)
+static void Cyber_MoveCursor (u_short x, u_short y)
{
*(CyberRegs + S3_CRTC_ADR) = 0x39;
*(CyberRegs + S3_CRTC_DATA) = 0xa0;
@@ -714,16 +707,20 @@ static struct fb_hwswitch Cyber_switch = {
* Fill the hardware's `par' structure.
*/
-static void Cyber_fb_get_par(struct Cyber_fb_par *par)
+static void cyberfb_get_par(struct cyberfb_par *par)
{
if (current_par_valid)
+ {
*par = current_par;
+ }
else
- fbhw->decode_var(&cyber_fb_predefined[Cyberfb_mode], par);
+ {
+ fbhw->decode_var(&cyberfb_default, par);
+ }
}
-static void Cyber_fb_set_par(struct Cyber_fb_par *par)
+static void cyberfb_set_par(struct cyberfb_par *par)
{
current_par = *par;
current_par_valid = 1;
@@ -733,6 +730,7 @@ static void Cyber_fb_set_par(struct Cyber_fb_par *par)
static void cyber_set_video(struct fb_var_screeninfo *var)
{
/* Set clipping rectangle to current screen size */
+
*((u_short volatile *)(CyberRegs + 0xbee8)) = 0x1000;
*((u_short volatile *)(CyberRegs + 0xbee8)) = 0x2000;
@@ -744,13 +742,13 @@ static void cyber_set_video(struct fb_var_screeninfo *var)
static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
{
int err, activate;
- struct Cyber_fb_par par;
+ struct cyberfb_par par;
if ((err = fbhw->decode_var(var, &par)))
return(err);
activate = var->activate;
if ((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW && isactive)
- Cyber_fb_set_par(&par);
+ cyberfb_set_par(&par);
fbhw->encode_var(var, &par);
var->activate = activate;
@@ -759,16 +757,16 @@ static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
}
-static void do_install_cmap(int con)
+static void do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
- &fb_display[con].var, 1, fbhw->setcolreg);
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, fbhw->setcolreg, info);
}
@@ -776,7 +774,7 @@ static void do_install_cmap(int con)
* Open/Release the frame buffer device
*/
-static int Cyber_fb_open(int fbidx)
+static int cyberfb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -786,7 +784,7 @@ static int Cyber_fb_open(int fbidx)
return(0);
}
-static int Cyber_fb_release(int fbidx)
+static int cyberfb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return(0);
@@ -797,13 +795,14 @@ static int Cyber_fb_release(int fbidx)
* Get the Fixed Part of the Display
*/
-static int Cyber_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
+static int cyberfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
{
- struct Cyber_fb_par par;
+ struct cyberfb_par par;
int error = 0;
if (con == -1)
- Cyber_fb_get_par(&par);
+ cyberfb_get_par(&par);
else
error = fbhw->decode_var(&fb_display[con].var, &par);
return(error ? error : fbhw->encode_fix(fix, &par));
@@ -814,21 +813,28 @@ static int Cyber_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
* Get the User Defined Part of the Display
*/
-static int Cyber_fb_get_var(struct fb_var_screeninfo *var, int con)
+static int cyberfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
- struct Cyber_fb_par par;
+ struct cyberfb_par par;
int error = 0;
- if (con == -1) {
- Cyber_fb_get_par(&par);
+ if (con == -1)
+ {
+ cyberfb_get_par(&par);
error = fbhw->encode_var(var, &par);
- } else
+ disp.var = *var; /* ++Andre: don't know if this is the right place */
+ }
+ else
+ {
*var = fb_display[con].var;
+ }
+
return(error);
}
-static void Cyber_fb_set_disp(int con)
+static void cyberfb_set_disp(int con, struct fb_info *info)
{
struct fb_fix_screeninfo fix;
struct display *display;
@@ -838,7 +844,7 @@ static void Cyber_fb_set_disp(int con)
else
display = &disp; /* used during initialization */
- Cyber_fb_get_fix(&fix, con);
+ cyberfb_get_fix(&fix, con, info);
if (con == -1)
con = 0;
display->screen_base = (u_char *)fix.smem_start;
@@ -849,6 +855,21 @@ static void Cyber_fb_set_disp(int con)
display->ywrapstep = fix.ywrapstep;
display->can_soft_blank = 1;
display->inverse = Cyberfb_inverse;
+ switch (display->var.bits_per_pixel) {
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_cyber8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ case 16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ break;
+ }
}
@@ -856,7 +877,8 @@ static void Cyber_fb_set_disp(int con)
* Set the User Defined Part of the Display
*/
-static int Cyber_fb_set_var(struct fb_var_screeninfo *var, int con)
+static int cyberfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
int err, oldxres, oldyres, oldvxres, oldvyres, oldbpp;
@@ -873,10 +895,10 @@ static int Cyber_fb_set_var(struct fb_var_screeninfo *var, int con)
oldvxres != var->xres_virtual ||
oldvyres != var->yres_virtual ||
oldbpp != var->bits_per_pixel) {
- Cyber_fb_set_disp(con);
+ cyberfb_set_disp(con, info);
(*fb_info.changevar)(con);
fb_alloc_cmap(&fb_display[con].cmap, 0, 0);
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
}
var->activate = 0;
@@ -888,15 +910,16 @@ static int Cyber_fb_set_var(struct fb_var_screeninfo *var, int con)
* Get the Colormap
*/
-static int Cyber_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int cyberfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
if (con == currcon) /* current console? */
return(fb_get_cmap(cmap, &fb_display[con].var,
- kspc, fbhw->getcolreg));
+ kspc, fbhw->getcolreg, info));
else if (fb_display[con].cmap.len) /* non default colormap? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return(0);
}
@@ -906,7 +929,8 @@ static int Cyber_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
* Set the Colormap
*/
-static int Cyber_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int cyberfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
int err;
@@ -915,9 +939,9 @@ static int Cyber_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
1<<fb_display[con].var.bits_per_pixel, 0)))
return(err);
}
- if (con == currcon) /* current console? */
+ if (con == currcon) /* current console? */
return(fb_set_cmap(cmap, &fb_display[con].var,
- kspc, fbhw->setcolreg));
+ kspc, fbhw->setcolreg, info));
else
fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
return(0);
@@ -930,31 +954,32 @@ static int Cyber_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
* This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
*/
-static int Cyber_fb_pan_display(struct fb_var_screeninfo *var, int con)
+static int cyberfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
return(-EINVAL);
}
/*
- * Cybervision Frame Buffer Specific ioctls
+ * Cybervision Frame Buffer Specific ioctls
*/
-static int Cyber_fb_ioctl(struct inode *inode, struct file *file,
- u_int cmd, u_long arg, int con)
+static int cyberfb_ioctl(struct inode *inode, struct file *file,
+ u_int cmd, u_long arg, int con, struct fb_info *info)
{
return(-EINVAL);
}
-static struct fb_ops Cyber_fb_ops = {
- Cyber_fb_open, Cyber_fb_release, Cyber_fb_get_fix, Cyber_fb_get_var,
- Cyber_fb_set_var, Cyber_fb_get_cmap, Cyber_fb_set_cmap,
- Cyber_fb_pan_display, Cyber_fb_ioctl
+static struct fb_ops cyberfb_ops = {
+ cyberfb_open, cyberfb_release, cyberfb_get_fix, cyberfb_get_var,
+ cyberfb_set_var, cyberfb_get_cmap, cyberfb_set_cmap,
+ cyberfb_pan_display, NULL, cyberfb_ioctl
};
-__initfunc(void Cyber_video_setup(char *options, int *ints))
+__initfunc(void cyberfb_setup(char *options, int *ints))
{
char *this_opt;
@@ -969,14 +994,18 @@ __initfunc(void Cyber_video_setup(char *options, int *ints))
fb_invert_cmaps();
} else if (!strncmp(this_opt, "font:", 5))
strcpy(fb_info.fontname, this_opt+5);
-#if 0
- else if (!strcmp (this_opt, "cyber8"))
- Cyberfb_Cyber8 = 1;
- else if (!strcmp (this_opt, "cyber16"))
- Cyberfb_Cyber16 = 1;
-#endif
+ else if (!strcmp (this_opt, "cyber8")){
+ cyberfb_default = cyberfb_predefined[CYBER8_DEFMODE].var;
+ }
+ else if (!strcmp (this_opt, "cyber16")){
+ cyberfb_default = cyberfb_predefined[CYBER16_DEFMODE].var;
+ }
else
- Cyberfb_mode = get_video_mode(this_opt);
+ get_video_mode(this_opt);
+
+ DPRINTK("default mode: xres=%d, yres=%d, bpp=%d\n",cyberfb_default.xres,
+ cyberfb_default.yres,
+ cyberfb_default.bits_per_pixel);
}
@@ -984,10 +1013,10 @@ __initfunc(void Cyber_video_setup(char *options, int *ints))
* Initialization
*/
-__initfunc(unsigned long Cyber_fb_init(unsigned long mem_start))
+__initfunc(unsigned long cyberfb_init(unsigned long mem_start))
{
int err;
- struct Cyber_fb_par par;
+ struct cyberfb_par par;
unsigned long board_addr;
const struct ConfigDev *cd;
@@ -1005,33 +1034,30 @@ __initfunc(unsigned long Cyber_fb_init(unsigned long mem_start))
fbhw = &Cyber_switch;
- strcpy(fb_info.modename, Cyber_fb_name);
+ strcpy(fb_info.modename, cyberfb_name);
fb_info.changevar = NULL;
fb_info.node = -1;
- fb_info.fbops = &Cyber_fb_ops;
- fb_info.fbvar_num = NUM_TOTAL_MODES;
- fb_info.fbvar = cyber_fb_predefined;
+ fb_info.fbops = &cyberfb_ops;
fb_info.disp = &disp;
fb_info.switch_con = &Cyberfb_switch;
fb_info.updatevar = &Cyberfb_updatevar;
fb_info.blank = &Cyberfb_blank;
- fb_info.setcmap = &Cyberfb_setcmap;
err = register_framebuffer(&fb_info);
if (err < 0)
return mem_start;
fbhw->init();
- fbhw->decode_var(&cyber_fb_predefined[Cyberfb_mode], &par);
- fbhw->encode_var(&cyber_fb_predefined[0], &par);
+ fbhw->decode_var(&cyberfb_default, &par);
+ fbhw->encode_var(&cyberfb_default, &par);
- do_fb_set_var(&cyber_fb_predefined[0], 1);
- Cyber_fb_get_var(&fb_display[0].var, -1);
- Cyber_fb_set_disp(-1);
- do_install_cmap(0);
+ do_fb_set_var(&cyberfb_default, 1);
+ cyberfb_get_var(&fb_display[0].var, -1, &fb_info);
+ cyberfb_set_disp(-1, &fb_info);
+ do_install_cmap(0, &fb_info);
- printk("%s frame buffer device, using %ldK of video memory\n",
- fb_info.modename, CyberSize>>10);
+ printk("fb%d: %s frame buffer device, using %ldK of video memory\n",
+ GET_FB_IDX(fb_info.node), fb_info.modename, CyberSize>>10);
/* TODO: This driver cannot be unloaded yet */
MOD_INC_USE_COUNT;
@@ -1040,17 +1066,17 @@ __initfunc(unsigned long Cyber_fb_init(unsigned long mem_start))
}
-static int Cyberfb_switch(int con)
+static int Cyberfb_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
- fbhw->getcolreg);
+ fbhw->getcolreg, info);
do_fb_set_var(&fb_display[con].var, 1);
currcon = con;
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return(0);
}
@@ -1062,7 +1088,7 @@ static int Cyberfb_switch(int con)
* Since it's called by a kernel driver, no range checking is done.
*/
-static int Cyberfb_updatevar(int con)
+static int Cyberfb_updatevar(int con, struct fb_info *info)
{
return(0);
}
@@ -1072,42 +1098,92 @@ static int Cyberfb_updatevar(int con)
* Blank the display.
*/
-static void Cyberfb_blank(int blank)
+static void Cyberfb_blank(int blank, struct fb_info *info)
{
fbhw->blank(blank);
}
/*
- * Set the colormap
+ * Get a Video Mode
*/
-static int Cyberfb_setcmap(struct fb_cmap *cmap, int con)
+__initfunc(static int get_video_mode(const char *name))
{
- return(Cyber_fb_set_cmap(cmap, 1, con));
+ int i;
+
+ for (i = 0; i < NUM_TOTAL_MODES; i++) {
+ if (!strcmp(name, cyberfb_predefined[i].name)) {
+ cyberfb_default = cyberfb_predefined[i].var;
+ return(i);
+ }
+ }
+ /* ++Andre: set cyberfb default mode */
+ cyberfb_default = cyberfb_predefined[CYBER8_DEFMODE].var;
+ return(0);
}
/*
- * Get a Video Mode
+ * Text console acceleration
*/
-static int get_video_mode(const char *name)
+#ifdef CONFIG_FBCON_CFB8
+static void fbcon_cyber8_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width)
{
- int i;
+ sx *= 8; dx *= 8; width *= 8;
+ Cyber_BitBLT((u_short)sx, (u_short)(sy*p->fontheight), (u_short)dx,
+ (u_short)(dy*p->fontheight), (u_short)width,
+ (u_short)(height*p->fontheight), (u_short)S3_NEW);
+}
- for (i = 1; i < NUM_PREDEF_MODES; i++)
- if (!strcmp(name, Cyber_fb_modenames[i]))
- cyber_fb_predefined[0] = cyber_fb_predefined[i];
- return(i);
- return(0);
+static void fbcon_cyber8_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
+{
+ unsigned char bg;
+
+ sx *= 8; width *= 8;
+ bg = attr_bgcol_ec(p,conp);
+ Cyber_RectFill((u_short)sx,
+ (u_short)(sy*p->fontheight),
+ (u_short)width,
+ (u_short)(height*p->fontheight),
+ (u_short)S3_NEW,
+ (u_short)bg);
+}
+
+static void fbcon_cyber8_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx)
+{
+ Cyber_WaitBlit();
+ fbcon_cfb8_putc(conp, p, c, yy, xx);
+}
+
+static void fbcon_cyber8_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx)
+{
+ Cyber_WaitBlit();
+ fbcon_cfb8_putcs(conp, p, s, count, yy, xx);
}
+static void fbcon_cyber8_revc(struct display *p, int xx, int yy)
+{
+ Cyber_WaitBlit();
+ fbcon_cfb8_revc(p, xx, yy);
+}
+
+static struct display_switch fbcon_cyber8 = {
+ fbcon_cfb8_setup, fbcon_cyber8_bmove, fbcon_cyber8_clear, fbcon_cyber8_putc,
+ fbcon_cyber8_putcs, fbcon_cyber8_revc
+};
+#endif
+
#ifdef MODULE
int init_module(void)
{
- return(Cyber_fb_init(NULL));
+ return(cyberfb_init(NULL));
}
void cleanup_module(void)
@@ -1118,12 +1194,3 @@ void cleanup_module(void)
/* TODO: clean up ... */
}
#endif /* MODULE */
-
-
-/*
- * Visible symbols for modules
- */
-
-EXPORT_SYMBOL(Cyber_BitBLT);
-EXPORT_SYMBOL(Cyber_RectFill);
-EXPORT_SYMBOL(Cyber_WaitBlit);
diff --git a/drivers/video/dn_fb.c b/drivers/video/dnfb.c
index 8c5aeb099..db0a6172f 100644
--- a/drivers/video/dn_fb.c
+++ b/drivers/video/dnfb.c
@@ -5,6 +5,7 @@
#include <linux/tty.h>
#include <linux/malloc.h>
#include <linux/delay.h>
+#include <linux/config.h>
#include <linux/interrupt.h>
#include <asm/setup.h>
#include <asm/segment.h>
@@ -14,6 +15,9 @@
#include <linux/fb.h>
#include <linux/module.h>
+#include "fbcon-mfb.h"
+
+
/* apollo video HW definitions */
/*
@@ -108,46 +112,44 @@
#endif
-void dn_video_setup(char *options, int *ints);
-
/* frame buffer operations */
-static int dn_fb_open(int fbidx);
-static int dn_fb_release(int fbidx);
-static int dn_fb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int dn_fb_get_var(struct fb_var_screeninfo *var, int con);
-static int dn_fb_set_var(struct fb_var_screeninfo *var, int isactive);
-static int dn_fb_get_cmap(struct fb_cmap *cmap,int kspc,int con);
-static int dn_fb_set_cmap(struct fb_cmap *cmap,int kspc,int con);
-static int dn_fb_pan_display(struct fb_var_screeninfo *var, int con);
-static int dn_fb_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
- unsigned long arg, int con);
-
-static int dnfbcon_switch(int con);
-static int dnfbcon_updatevar(int con);
-static void dnfbcon_blank(int blank);
-
-static void dn_fb_set_disp(int con);
+static int dnfb_open(struct fb_info *info);
+static int dnfb_release(struct fb_info *info);
+static int dnfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int dnfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int dnfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int dnfb_get_cmap(struct fb_cmap *cmap,int kspc,int con,
+ struct fb_info *info);
+static int dnfb_set_cmap(struct fb_cmap *cmap,int kspc,int con,
+ struct fb_info *info);
+static int dnfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int dnfb_ioctl(struct inode *inode, struct file *file,
+ unsigned int cmd, unsigned long arg, int con,
+ struct fb_info *info);
+
+static int dnfbcon_switch(int con, struct fb_info *info);
+static int dnfbcon_updatevar(int con, struct fb_info *info);
+static void dnfbcon_blank(int blank, struct fb_info *info);
+
+static void dnfb_set_disp(int con, struct fb_info *info);
static struct display disp[MAX_NR_CONSOLES];
static struct fb_info fb_info;
-static struct fb_ops dn_fb_ops = {
- dn_fb_open,dn_fb_release, dn_fb_get_fix, dn_fb_get_var, dn_fb_set_var,
- dn_fb_get_cmap, dn_fb_set_cmap, dn_fb_pan_display, dn_fb_ioctl
+static struct fb_ops dnfb_ops = {
+ dnfb_open,dnfb_release, dnfb_get_fix, dnfb_get_var, dnfb_set_var,
+ dnfb_get_cmap, dnfb_set_cmap, dnfb_pan_display, NULL, dnfb_ioctl
};
static int currcon=0;
-#define NUM_TOTAL_MODES 1
-struct fb_var_screeninfo dn_fb_predefined[] = {
-
- { 0, },
+static char dnfb_name[]="Apollo";
-};
-
-static char dn_fb_name[]="Apollo ";
-
-static int dn_fb_open(int fbidx)
+static int dnfb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -157,14 +159,15 @@ static int dn_fb_open(int fbidx)
return(0);
}
-static int dn_fb_release(int fbidx)
+static int dnfb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return(0);
}
-static int dn_fb_get_fix(struct fb_fix_screeninfo *fix, int con) {
-
+static int dnfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
+{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id,"Apollo Mono");
fix->smem_start=(char*)(FRAME_BUFFER_START+IO_BASE);
@@ -181,8 +184,9 @@ static int dn_fb_get_fix(struct fb_fix_screeninfo *fix, int con) {
}
-static int dn_fb_get_var(struct fb_var_screeninfo *var, int con) {
-
+static int dnfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
var->xres=1280;
var->yres=1024;
var->xres_virtual=2048;
@@ -208,9 +212,9 @@ static int dn_fb_get_var(struct fb_var_screeninfo *var, int con) {
}
-static int dn_fb_set_var(struct fb_var_screeninfo *var, int isactive) {
-
- printk("fb_set_var\n");
+static int dnfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
if(var->xres!=1280)
return -EINVAL;
if(var->yres!=1024)
@@ -252,48 +256,48 @@ static int dn_fb_set_var(struct fb_var_screeninfo *var, int isactive) {
}
-static int dn_fb_get_cmap(struct fb_cmap *cmap,int kspc,int con) {
-
+static int dnfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
printk("get cmap not supported\n");
return -EINVAL;
}
-static int dn_fb_set_cmap(struct fb_cmap *cmap,int kspc,int con) {
-
+static int dnfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
printk("set cmap not supported\n");
return -EINVAL;
}
-static int dn_fb_pan_display(struct fb_var_screeninfo *var, int con) {
-
+static int dnfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
printk("panning not supported\n");
return -EINVAL;
}
-static int dn_fb_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
- unsigned long arg, int con) {
-
- printk("no IOCTLs as of yet.\n");
-
+static int dnfb_ioctl(struct inode *inode, struct file *file,
+ unsigned int cmd, unsigned long arg, int con,
+ struct fb_info *info)
+{
return -EINVAL;
-
}
-static void dn_fb_set_disp(int con) {
-
+static void dnfb_set_disp(int con, struct fb_info *info)
+{
struct fb_fix_screeninfo fix;
- dn_fb_get_fix(&fix,con);
+ dnfb_get_fix(&fix, con, info);
if(con==-1)
con=0;
disp[con].screen_base = (u_char *)fix.smem_start;
-printk("screenbase: %p\n",fix.smem_start);
disp[con].visual = fix.visual;
disp[con].type = fix.type;
disp[con].type_aux = fix.type_aux;
@@ -302,27 +306,27 @@ printk("screenbase: %p\n",fix.smem_start);
disp[con].can_soft_blank = 1;
disp[con].inverse = 0;
disp[con].line_length = fix.line_length;
+#ifdef CONFIG_FBCON_MFB
+ disp[con].dispsw = &fbcon_mfb;
+#else
+ disp[con].dispsw = NULL;
+#endif
}
-unsigned long dn_fb_init(unsigned long mem_start) {
-
+unsigned long dnfb_init(unsigned long mem_start)
+{
int err;
-printk("dn_fb_init\n");
-
fb_info.changevar=NULL;
- strcpy(&fb_info.modename[0],dn_fb_name);
+ strcpy(&fb_info.modename[0],dnfb_name);
fb_info.fontname[0]=0;
fb_info.disp=disp;
fb_info.switch_con=&dnfbcon_switch;
fb_info.updatevar=&dnfbcon_updatevar;
fb_info.blank=&dnfbcon_blank;
fb_info.node = -1;
- fb_info.fbops = &dn_fb_ops;
- fb_info.fbvar = dn_fb_predefined;
- fb_info.fbvar_num = NUM_TOTAL_MODES;
+ fb_info.fbops = &dnfb_ops;
-printk("dn_fb_init: register\n");
err=register_framebuffer(&fb_info);
if(err < 0) {
panic("unable to register apollo frame buffer\n");
@@ -337,35 +341,34 @@ printk("dn_fb_init: register\n");
outb(S_DATA_PLN, AP_CONTROL_2);
outw(SWAP(0x3),AP_ROP_1);
- printk("apollo frame buffer alive and kicking !\n");
+ printk("fb%d: apollo frame buffer alive and kicking !\n",
+ GET_FB_IDX(fb_info.node));
- dn_fb_get_var(&disp[0].var,0);
+ dnfb_get_var(&disp[0].var, 0, &fb_info);
- dn_fb_set_disp(-1);
+ dnfb_set_disp(-1, &fb_info);
return mem_start;
}
-static int dnfbcon_switch(int con) {
-
+static int dnfbcon_switch(int con, struct fb_info *info)
+{
currcon=con;
return 0;
}
-static int dnfbcon_updatevar(int con) {
-
+static int dnfbcon_updatevar(int con, struct fb_info *info)
+{
return 0;
-
}
-static void dnfbcon_blank(int blank) {
-
- printk("dnfbcon_blank: %d\n",blank);
+static void dnfbcon_blank(int blank, struct fb_info *info)
+{
if(blank) {
outb(0, AP_CONTROL_3A);
outb((AD_BLT | DST_EQ_SRC | NORM_CREG1) & ~ENAB_DISP,
@@ -375,14 +378,4 @@ static void dnfbcon_blank(int blank) {
outb(1, AP_CONTROL_3A);
outb((AD_BLT | DST_EQ_SRC | NORM_CREG1), AP_CONTROL_1);
}
-
- return ;
-
}
-
-void dn_video_setup(char *options, int *ints) {
-
- return;
-
-}
-
diff --git a/drivers/video/fbcmap.c b/drivers/video/fbcmap.c
index 9f3c586c7..bbf06d89b 100644
--- a/drivers/video/fbcmap.c
+++ b/drivers/video/fbcmap.c
@@ -35,45 +35,45 @@ static void memcpy_fs(int fsfromto, void *to, void *from, int len)
#define CNVT_FROMHW(val,width) (((width) ? ((((val)<<16)-(val)) / \
((1<<(width))-1)) : 0))
-static u_short red2[] = {
+static u16 red2[] = {
0x0000, 0xaaaa
};
-static u_short green2[] = {
+static u16 green2[] = {
0x0000, 0xaaaa
};
-static u_short blue2[] = {
+static u16 blue2[] = {
0x0000, 0xaaaa
-};
-
-static u_short red4[] = {
+};
+
+static u16 red4[] = {
0x0000, 0xaaaa, 0x5555, 0xffff
};
-static u_short green4[] = {
+static u16 green4[] = {
0x0000, 0xaaaa, 0x5555, 0xffff
};
-static u_short blue4[] = {
+static u16 blue4[] = {
0x0000, 0xaaaa, 0x5555, 0xffff
};
-
-static u_short red8[] = {
+
+static u16 red8[] = {
0x0000, 0x0000, 0x0000, 0x0000, 0xaaaa, 0xaaaa, 0xaaaa, 0xaaaa
};
-static u_short green8[] = {
+static u16 green8[] = {
0x0000, 0x0000, 0xaaaa, 0xaaaa, 0x0000, 0x0000, 0xaaaa, 0xaaaa
};
-static u_short blue8[] = {
+static u16 blue8[] = {
0x0000, 0xaaaa, 0x0000, 0xaaaa, 0x0000, 0xaaaa, 0x0000, 0xaaaa
};
-
-static u_short red16[] = {
+
+static u16 red16[] = {
0x0000, 0x0000, 0x0000, 0x0000, 0xaaaa, 0xaaaa, 0xaaaa, 0xaaaa,
0x5555, 0x5555, 0x5555, 0x5555, 0xffff, 0xffff, 0xffff, 0xffff
};
-static u_short green16[] = {
+static u16 green16[] = {
0x0000, 0x0000, 0xaaaa, 0xaaaa, 0x0000, 0x0000, 0xaaaa, 0xaaaa,
0x5555, 0x5555, 0xffff, 0xffff, 0x5555, 0x5555, 0xffff, 0xffff
};
-static u_short blue16[] = {
+static u16 blue16[] = {
0x0000, 0xaaaa, 0x0000, 0xaaaa, 0x0000, 0xaaaa, 0x0000, 0xaaaa,
0x5555, 0xffff, 0x5555, 0xffff, 0x5555, 0xffff, 0x5555, 0xffff
};
@@ -83,10 +83,10 @@ static struct fb_cmap default_2_colors = {
};
static struct fb_cmap default_8_colors = {
0, 8, red8, green8, blue8, NULL
-};
+};
static struct fb_cmap default_4_colors = {
0, 4, red4, green4, blue4, NULL
-};
+};
static struct fb_cmap default_16_colors = {
0, 16, red16, green16, blue16, NULL
};
@@ -98,32 +98,32 @@ static struct fb_cmap default_16_colors = {
int fb_alloc_cmap(struct fb_cmap *cmap, int len, int transp)
{
- int size = len*sizeof(u_short);
-
+ int size = len*sizeof(u16);
+
if (cmap->len != len) {
- if (cmap->red)
+ if (cmap->red)
kfree(cmap->red);
if (cmap->green)
kfree(cmap->green);
if (cmap->blue)
kfree(cmap->blue);
if (cmap->transp)
- kfree(cmap->transp);
- cmap->red = cmap->green = cmap->blue = cmap->transp = NULL;
- cmap->len = 0;
- if (!len)
- return 0;
+ kfree(cmap->transp);
+ cmap->red = cmap->green = cmap->blue = cmap->transp = NULL;
+ cmap->len = 0;
+ if (!len)
+ return 0;
if (!(cmap->red = kmalloc(size, GFP_ATOMIC)))
return -1;
- if (!(cmap->green = kmalloc(size, GFP_ATOMIC)))
+ if (!(cmap->green = kmalloc(size, GFP_ATOMIC)))
return -1;
if (!(cmap->blue = kmalloc(size, GFP_ATOMIC)))
- return -1;
- if (transp) {
+ return -1;
+ if (transp) {
if (!(cmap->transp = kmalloc(size, GFP_ATOMIC)))
- return -1;
- } else
- cmap->transp = NULL;
+ return -1;
+ } else
+ cmap->transp = NULL;
}
cmap->start = 0;
cmap->len = len;
@@ -150,12 +150,12 @@ void fb_copy_cmap(struct fb_cmap *from, struct fb_cmap *to, int fsfromto)
size = from->len-fromoff;
if (size < 0)
return;
- size *= sizeof(u_short);
+ size *= sizeof(u16);
memcpy_fs(fsfromto, to->red+tooff, from->red+fromoff, size);
memcpy_fs(fsfromto, to->green+tooff, from->green+fromoff, size);
memcpy_fs(fsfromto, to->blue+tooff, from->blue+fromoff, size);
if (from->transp && to->transp)
- memcpy_fs(fsfromto, to->transp+tooff, from->transp+fromoff, size);
+ memcpy_fs(fsfromto, to->transp+tooff, from->transp+fromoff, size);
}
@@ -164,10 +164,11 @@ void fb_copy_cmap(struct fb_cmap *from, struct fb_cmap *to, int fsfromto)
*/
int fb_get_cmap(struct fb_cmap *cmap, struct fb_var_screeninfo *var, int kspc,
- int (*getcolreg)(u_int, u_int *, u_int *, u_int *, u_int *))
+ int (*getcolreg)(u_int, u_int *, u_int *, u_int *, u_int *,
+ struct fb_info *), struct fb_info *info)
{
int i, start;
- u_short *red, *green, *blue, *transp;
+ u16 *red, *green, *blue, *transp;
u_int hred, hgreen, hblue, htransp;
red = cmap->red;
@@ -178,7 +179,7 @@ int fb_get_cmap(struct fb_cmap *cmap, struct fb_var_screeninfo *var, int kspc,
if (start < 0)
return -EINVAL;
for (i = 0; i < cmap->len; i++) {
- if (getcolreg(start++, &hred, &hgreen, &hblue, &htransp))
+ if (getcolreg(start++, &hred, &hgreen, &hblue, &htransp, info))
return 0;
hred = CNVT_FROMHW(hred, var->red.length);
hgreen = CNVT_FROMHW(hgreen, var->green.length);
@@ -212,10 +213,11 @@ int fb_get_cmap(struct fb_cmap *cmap, struct fb_var_screeninfo *var, int kspc,
*/
int fb_set_cmap(struct fb_cmap *cmap, struct fb_var_screeninfo *var, int kspc,
- int (*setcolreg)(u_int, u_int, u_int, u_int, u_int))
+ int (*setcolreg)(u_int, u_int, u_int, u_int, u_int,
+ struct fb_info *), struct fb_info *info)
{
int i, start;
- u_short *red, *green, *blue, *transp;
+ u16 *red, *green, *blue, *transp;
u_int hred, hgreen, hblue, htransp;
red = cmap->red;
@@ -250,7 +252,7 @@ int fb_set_cmap(struct fb_cmap *cmap, struct fb_var_screeninfo *var, int kspc,
blue++;
if (transp)
transp++;
- if (setcolreg(start++, hred, hgreen, hblue, htransp))
+ if (setcolreg(start++, hred, hgreen, hblue, htransp, info))
return 0;
}
return 0;
@@ -261,22 +263,15 @@ int fb_set_cmap(struct fb_cmap *cmap, struct fb_var_screeninfo *var, int kspc,
* Get the default colormap for a specific screen depth
*/
-struct fb_cmap *fb_default_cmap(int bpp)
+struct fb_cmap *fb_default_cmap(int len)
{
- switch (bpp) {
- case 1:
- return &default_2_colors;
- break;
- case 2:
- return &default_4_colors;
- break;
- case 3:
- return &default_8_colors;
- break;
- default:
- return &default_16_colors;
- break;
- }
+ if (len <= 2)
+ return &default_2_colors;
+ if (len <= 4)
+ return &default_4_colors;
+ if (len <= 8)
+ return &default_8_colors;
+ return &default_16_colors;
}
diff --git a/drivers/video/fbcon-afb.c b/drivers/video/fbcon-afb.c
index a56323041..66132809a 100644
--- a/drivers/video/fbcon-afb.c
+++ b/drivers/video/fbcon-afb.c
@@ -13,132 +13,242 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
#include "fbcon.h"
+#include "fbcon-afb.h"
/*
- * Prototypes
- */
-
-static int open_afb(struct display *p);
-static void release_afb(void);
-static void bmove_afb(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_afb(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width);
-static void putc_afb(struct vc_data *conp, struct display *p, int c, int yy,
- int xx);
-static void putcs_afb(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx);
-static void rev_char_afb(struct display *p, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
+ * Bitplanes ŕ la Amiga
*/
-static struct display_switch dispsw_afb = {
- open_afb, release_afb, bmove_afb, clear_afb, putc_afb, putcs_afb,
- rev_char_afb
+static u8 expand_table[1024] = {
+ /* bg = fg = 0 */
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ /* bg = 0, fg = 1 */
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
+ 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
+ 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
+ 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
+ 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
+ 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
+ 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
+ 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
+ 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,
+ 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
+ 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,
+ 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
+ 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,
+ 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
+ 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f,
+ 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
+ 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f,
+ 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
+ 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f,
+ 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
+ 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf,
+ 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7,
+ 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf,
+ 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7,
+ 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf,
+ 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7,
+ 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf,
+ 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7,
+ 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef,
+ 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
+ 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff,
+ /* bg = 1, fg = 0 */
+ 0xff, 0xfe, 0xfd, 0xfc, 0xfb, 0xfa, 0xf9, 0xf8,
+ 0xf7, 0xf6, 0xf5, 0xf4, 0xf3, 0xf2, 0xf1, 0xf0,
+ 0xef, 0xee, 0xed, 0xec, 0xeb, 0xea, 0xe9, 0xe8,
+ 0xe7, 0xe6, 0xe5, 0xe4, 0xe3, 0xe2, 0xe1, 0xe0,
+ 0xdf, 0xde, 0xdd, 0xdc, 0xdb, 0xda, 0xd9, 0xd8,
+ 0xd7, 0xd6, 0xd5, 0xd4, 0xd3, 0xd2, 0xd1, 0xd0,
+ 0xcf, 0xce, 0xcd, 0xcc, 0xcb, 0xca, 0xc9, 0xc8,
+ 0xc7, 0xc6, 0xc5, 0xc4, 0xc3, 0xc2, 0xc1, 0xc0,
+ 0xbf, 0xbe, 0xbd, 0xbc, 0xbb, 0xba, 0xb9, 0xb8,
+ 0xb7, 0xb6, 0xb5, 0xb4, 0xb3, 0xb2, 0xb1, 0xb0,
+ 0xaf, 0xae, 0xad, 0xac, 0xab, 0xaa, 0xa9, 0xa8,
+ 0xa7, 0xa6, 0xa5, 0xa4, 0xa3, 0xa2, 0xa1, 0xa0,
+ 0x9f, 0x9e, 0x9d, 0x9c, 0x9b, 0x9a, 0x99, 0x98,
+ 0x97, 0x96, 0x95, 0x94, 0x93, 0x92, 0x91, 0x90,
+ 0x8f, 0x8e, 0x8d, 0x8c, 0x8b, 0x8a, 0x89, 0x88,
+ 0x87, 0x86, 0x85, 0x84, 0x83, 0x82, 0x81, 0x80,
+ 0x7f, 0x7e, 0x7d, 0x7c, 0x7b, 0x7a, 0x79, 0x78,
+ 0x77, 0x76, 0x75, 0x74, 0x73, 0x72, 0x71, 0x70,
+ 0x6f, 0x6e, 0x6d, 0x6c, 0x6b, 0x6a, 0x69, 0x68,
+ 0x67, 0x66, 0x65, 0x64, 0x63, 0x62, 0x61, 0x60,
+ 0x5f, 0x5e, 0x5d, 0x5c, 0x5b, 0x5a, 0x59, 0x58,
+ 0x57, 0x56, 0x55, 0x54, 0x53, 0x52, 0x51, 0x50,
+ 0x4f, 0x4e, 0x4d, 0x4c, 0x4b, 0x4a, 0x49, 0x48,
+ 0x47, 0x46, 0x45, 0x44, 0x43, 0x42, 0x41, 0x40,
+ 0x3f, 0x3e, 0x3d, 0x3c, 0x3b, 0x3a, 0x39, 0x38,
+ 0x37, 0x36, 0x35, 0x34, 0x33, 0x32, 0x31, 0x30,
+ 0x2f, 0x2e, 0x2d, 0x2c, 0x2b, 0x2a, 0x29, 0x28,
+ 0x27, 0x26, 0x25, 0x24, 0x23, 0x22, 0x21, 0x20,
+ 0x1f, 0x1e, 0x1d, 0x1c, 0x1b, 0x1a, 0x19, 0x18,
+ 0x17, 0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10,
+ 0x0f, 0x0e, 0x0d, 0x0c, 0x0b, 0x0a, 0x09, 0x08,
+ 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00,
+ /* bg = fg = 1 */
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
};
- /*
- * Bitplanes ŕ la Amiga
- */
-
-static int open_afb(struct display *p)
+void fbcon_afb_setup(struct display *p)
{
- if (p->type != FB_TYPE_PLANES)
- return -EINVAL;
-
if (p->line_length)
p->next_line = p->line_length;
else
p->next_line = p->var.xres_virtual>>3;
p->next_plane = p->var.yres_virtual*p->next_line;
- MOD_INC_USE_COUNT;
- return 0;
}
-static void release_afb(void)
+void fbcon_afb_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_afb(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
-{
- u_char *src, *dest, *src0, *dest0;
- u_int i, rows;
+ u8 *src, *dest, *src0, *dest0;
+ u_short i, j;
if (sx == 0 && dx == 0 && width == p->next_line) {
src = p->screen_base+sy*p->fontheight*width;
dest = p->screen_base+dy*p->fontheight*width;
- for (i = p->var.bits_per_pixel; i--;) {
+ i = p->var.bits_per_pixel;
+ do {
mymemmove(dest, src, height*p->fontheight*width);
src += p->next_plane;
dest += p->next_plane;
- }
+ } while (--i);
} else if (dy <= sy) {
src0 = p->screen_base+sy*p->fontheight*p->next_line+sx;
dest0 = p->screen_base+dy*p->fontheight*p->next_line+dx;
- for (i = p->var.bits_per_pixel; i--;) {
+ i = p->var.bits_per_pixel;
+ do {
src = src0;
dest = dest0;
- for (rows = height*p->fontheight; rows--;) {
+ j = height*p->fontheight;
+ do {
mymemmove(dest, src, width);
src += p->next_line;
dest += p->next_line;
- }
+ } while (--j);
src0 += p->next_plane;
dest0 += p->next_plane;
- }
+ } while (--i);
} else {
src0 = p->screen_base+(sy+height)*p->fontheight*p->next_line+sx;
dest0 = p->screen_base+(dy+height)*p->fontheight*p->next_line+dx;
- for (i = p->var.bits_per_pixel; i--;) {
+ i = p->var.bits_per_pixel;
+ do {
src = src0;
dest = dest0;
- for (rows = height*p->fontheight; rows--;) {
+ j = height*p->fontheight;
+ do {
src -= p->next_line;
dest -= p->next_line;
mymemmove(dest, src, width);
- }
+ } while (--j);
src0 += p->next_plane;
dest0 += p->next_plane;
- }
+ } while (--i);
}
}
-static void clear_afb(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width)
+void fbcon_afb_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
{
- u_char *dest, *dest0;
- u_int i, rows;
+ u8 *dest, *dest0;
+ u_short i, j;
int bg;
dest0 = p->screen_base+sy*p->fontheight*p->next_line+sx;
bg = attr_bgcol_ec(p,conp);
- for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
+ i = p->var.bits_per_pixel;
+ do {
dest = dest0;
- for (rows = height*p->fontheight; rows--; dest += p->next_line)
+ j = height*p->fontheight;
+ do {
if (bg & 1)
mymemset(dest, width);
else
mymemclear(dest, width);
+ dest += p->next_line;
+ } while (--j);
bg >>= 1;
- }
+ dest0 += p->next_plane;
+ } while (--i);
}
-static void putc_afb(struct vc_data *conp, struct display *p, int c, int yy,
- int xx)
+void fbcon_afb_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
{
- u_char *dest, *dest0, *cdat, *cdat0;
- u_int rows, i;
- u_char d;
+ u8 *dest, *dest0, *cdat, *cdat0, *expand;
+ u_short i, j;
int fg, bg;
c &= 0xff;
@@ -148,25 +258,24 @@ static void putc_afb(struct vc_data *conp, struct display *p, int c, int yy,
fg = attr_fgcol(p,conp);
bg = attr_bgcol(p,conp);
- for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
+ i = p->var.bits_per_pixel;
+ do {
dest = dest0;
cdat = cdat0;
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat++;
- if (bg & 1)
- if (fg & 1)
- *dest = 0xff;
- else
- *dest = ~d;
- else
- if (fg & 1)
- *dest = d;
- else
- *dest = 0x00;
- }
+ expand = expand_table;
+ if (bg & 1)
+ expand += 512;
+ if (fg & 1)
+ expand += 256;
+ j = p->fontheight;
+ do {
+ *dest = expand[*cdat++];
+ dest += p->next_line;
+ } while (--j);
bg >>= 1;
fg >>= 1;
- }
+ dest0 += p->next_plane;
+ } while (--i);
}
/*
@@ -174,14 +283,13 @@ static void putc_afb(struct vc_data *conp, struct display *p, int c, int yy,
* (cfr. fbcon_putcs_ilbm())
*/
-static void putcs_afb(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx)
+void fbcon_afb_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
{
- u_char *dest, *dest0, *dest1;
- u_char *cdat1, *cdat2, *cdat3, *cdat4, *cdat10, *cdat20, *cdat30, *cdat40;
- u_int rows, i;
- u_char c1, c2, c3, c4;
- u_long d;
+ u8 *dest, *dest0, *dest1, *expand;
+ u8 *cdat1, *cdat2, *cdat3, *cdat4, *cdat10, *cdat20, *cdat30, *cdat40;
+ u_short i, j;
+ u8 c1, c2, c3, c4;
int fg0, bg0, fg, bg;
dest0 = p->screen_base+yy*p->fontheight*p->next_line+xx;
@@ -198,26 +306,25 @@ static void putcs_afb(struct vc_data *conp, struct display *p, const char *s,
fg = fg0;
bg = bg0;
- for (i = p->var.bits_per_pixel; i--; dest1 += p->next_plane) {
+ i = p->var.bits_per_pixel;
+ do {
dest = dest1;
cdat1 = cdat10;
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat1++;
- if (bg & 1)
- if (fg & 1)
- *dest = 0xff;
- else
- *dest = ~d;
- else
- if (fg & 1)
- *dest = d;
- else
- *dest = 0x00;
- }
+ expand = expand_table;
+ if (bg & 1)
+ expand += 512;
+ if (fg & 1)
+ expand += 256;
+ j = p->fontheight;
+ do {
+ *dest = expand[*cdat1++];
+ dest += p->next_line;
+ } while (--j);
bg >>= 1;
fg >>= 1;
- }
- } else { /* Fast version */
+ dest1 += p->next_plane;
+ } while (--i);
+ } else { /* Fast version */
c1 = s[0];
c2 = s[1];
c3 = s[2];
@@ -231,28 +338,39 @@ static void putcs_afb(struct vc_data *conp, struct display *p, const char *s,
fg = fg0;
bg = bg0;
- for (i = p->var.bits_per_pixel; i--; dest1 += p->next_plane) {
+ i = p->var.bits_per_pixel;
+ do {
dest = dest1;
cdat1 = cdat10;
cdat2 = cdat20;
cdat3 = cdat30;
cdat4 = cdat40;
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat1++<<24 | *cdat2++<<16 | *cdat3++<<8 | *cdat4++;
- if (bg & 1)
- if (fg & 1)
- *(u_long *)dest = 0xffffffff;
- else
- *(u_long *)dest = ~d;
- else
- if (fg & 1)
- *(u_long *)dest = d;
- else
- *(u_long *)dest = 0x00000000;
- }
+ expand = expand_table;
+ if (bg & 1)
+ expand += 512;
+ if (fg & 1)
+ expand += 256;
+ j = p->fontheight;
+ do {
+#if defined(__BIG_ENDIAN)
+ *(u32 *)dest = expand[*cdat1++]<<24 |
+ expand[*cdat2++]<<16 |
+ expand[*cdat3++]<<8 |
+ expand[*cdat4++];
+#elif defined(__LITTLE_ENDIAN)
+ *(u32 *)dest = expand[*cdat1++] |
+ expand[*cdat2++]<<8 |
+ expand[*cdat3++]<<16 |
+ expand[*cdat4++]<<24;
+#else
+#error FIXME: No endianness??
+#endif
+ dest += p->next_line;
+ } while (--j);
bg >>= 1;
fg >>= 1;
- }
+ dest1 += p->next_plane;
+ } while (--i);
s += 4;
dest0 += 4;
xx += 4;
@@ -260,10 +378,10 @@ static void putcs_afb(struct vc_data *conp, struct display *p, const char *s,
}
}
-static void rev_char_afb(struct display *p, int xx, int yy)
+void fbcon_afb_revc(struct display *p, int xx, int yy)
{
- u_char *dest, *dest0;
- u_int rows, i;
+ u8 *dest, *dest0;
+ u_short i, j;
int mask;
dest0 = p->screen_base+yy*p->fontheight*p->next_line+xx;
@@ -275,29 +393,40 @@ static void rev_char_afb(struct display *p, int xx, int yy)
* inverting.
*/
- for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
+ i = p->var.bits_per_pixel;
+ do {
if (mask & 1) {
dest = dest0;
- for (rows = p->fontheight; rows--; dest += p->next_line)
+ j = p->fontheight;
+ do {
*dest = ~*dest;
+ dest += p->next_line;
+ } while (--j);
}
mask >>= 1;
- }
+ dest0 += p->next_plane;
+ } while (--i);
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_afb(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_afb, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_afb);
-}
-#endif /* MODULE */
+struct display_switch fbcon_afb = {
+ fbcon_afb_setup, fbcon_afb_bmove, fbcon_afb_clear, fbcon_afb_putc,
+ fbcon_afb_putcs, fbcon_afb_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_afb);
+EXPORT_SYMBOL(fbcon_afb_setup);
+EXPORT_SYMBOL(fbcon_afb_bmove);
+EXPORT_SYMBOL(fbcon_afb_clear);
+EXPORT_SYMBOL(fbcon_afb_putc);
+EXPORT_SYMBOL(fbcon_afb_putcs);
+EXPORT_SYMBOL(fbcon_afb_revc);
diff --git a/drivers/video/fbcon-afb.h b/drivers/video/fbcon-afb.h
new file mode 100644
index 000000000..537b3bdd7
--- /dev/null
+++ b/drivers/video/fbcon-afb.h
@@ -0,0 +1,15 @@
+ /*
+ * Amiga bitplanes (afb)
+ */
+
+extern struct display_switch fbcon_afb;
+extern void fbcon_afb_setup(struct display *p);
+extern void fbcon_afb_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_afb_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_afb_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_afb_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_afb_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cfb16.c b/drivers/video/fbcon-cfb16.c
index 8bd58ce8a..b27683c95 100644
--- a/drivers/video/fbcon-cfb16.c
+++ b/drivers/video/fbcon-cfb16.c
@@ -1,6 +1,6 @@
/*
* linux/drivers/video/cfb16.c -- Low level frame buffer operations for 16 bpp
- * packed pixels
+ * truecolor packed pixels
*
* Created 5 Apr 1997 by Geert Uytterhoeven
*
@@ -13,69 +13,40 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
#include "fbcon.h"
-
-
- /*
- * Prototypes
- */
-
-static int open_cfb16(struct display *p);
-static void release_cfb16(void);
-static void bmove_cfb16(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_cfb16(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width);
-static void putc_cfb16(struct vc_data *conp, struct display *p, int c,
- int yy, int xx);
-static void putcs_cfb16(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx);
-static void rev_char_cfb16(struct display *p, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_cfb16 = {
- open_cfb16, release_cfb16, bmove_cfb16, clear_cfb16, putc_cfb16,
- putcs_cfb16, rev_char_cfb16
-};
+#include "fbcon-cfb16.h"
/*
* 16 bpp packed pixels
*/
-u_short packed16_cmap[16];
+u16 fbcon_cfb16_cmap[16];
-static u_long tab_cfb16[] = {
- 0x00000000,0x0000ffff,0xffff0000,0xffffffff
+static u32 tab_cfb16[] = {
+#if defined(__BIG_ENDIAN)
+ 0x00000000, 0x0000ffff, 0xffff0000, 0xffffffff
+#elif defined(__LITTLE_ENDIAN)
+ 0x00000000, 0xffff0000, 0x0000ffff, 0xffffffff
+#else
+#error FIXME: No endianness??
+#endif
};
-static int open_cfb16(struct display *p)
+void fbcon_cfb16_setup(struct display *p)
{
- if (p->type != FB_TYPE_PACKED_PIXELS || p->var.bits_per_pixel != 16)
- return -EINVAL;
-
p->next_line = p->var.xres_virtual<<1;
p->next_plane = 0;
- MOD_INC_USE_COUNT;
- return 0;
-}
-
-static void release_cfb16(void)
-{
- MOD_DEC_USE_COUNT;
}
-static void bmove_cfb16(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
+void fbcon_cfb16_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
- u_char *src,*dst;
+ u8 *src, *dst;
if (sx == 0 && dx == 0 && width * 16 == bytes)
mymemmove(p->screen_base + dy * linesize,
@@ -100,82 +71,78 @@ static void bmove_cfb16(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_cfb16(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width)
+void fbcon_cfb16_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
{
- u_char *dest0,*dest;
- int bytes=p->next_line,lines=height * p->fontheight, rows, i;
- u_long bgx;
+ u8 *dest0, *dest;
+ int bytes = p->next_line, lines = height * p->fontheight, rows, i;
+ u32 bgx;
dest = p->screen_base + sy * p->fontheight * bytes + sx * 16;
- bgx = attr_bgcol_ec(p,conp);
- bgx = packed16_cmap[bgx];
+ bgx = fbcon_cfb16_cmap[attr_bgcol_ec(p, conp)];
bgx |= (bgx << 16);
if (sx == 0 && width * 16 == bytes)
for (i = 0 ; i < lines * width ; i++) {
- ((u_long *)dest)[0]=bgx;
- ((u_long *)dest)[1]=bgx;
- ((u_long *)dest)[2]=bgx;
- ((u_long *)dest)[3]=bgx;
- dest+=16;
+ ((u32 *)dest)[0] = bgx;
+ ((u32 *)dest)[1] = bgx;
+ ((u32 *)dest)[2] = bgx;
+ ((u32 *)dest)[3] = bgx;
+ dest += 16;
}
else {
- dest0=dest;
+ dest0 = dest;
for (rows = lines; rows-- ; dest0 += bytes) {
- dest=dest0;
+ dest = dest0;
for (i = 0 ; i < width ; i++) {
- ((u_long *)dest)[0]=bgx;
- ((u_long *)dest)[1]=bgx;
- ((u_long *)dest)[2]=bgx;
- ((u_long *)dest)[3]=bgx;
- dest+=16;
+ ((u32 *)dest)[0] = bgx;
+ ((u32 *)dest)[1] = bgx;
+ ((u32 *)dest)[2] = bgx;
+ ((u32 *)dest)[3] = bgx;
+ dest += 16;
}
}
}
}
-static void putc_cfb16(struct vc_data *conp, struct display *p, int c, int yy,
- int xx)
+void fbcon_cfb16_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
{
- u_char *dest,*cdat;
- int bytes=p->next_line,rows;
- ulong eorx,fgx,bgx;
+ u8 *dest, *cdat;
+ int bytes = p->next_line, rows;
+ u32 eorx, fgx, bgx;
c &= 0xff;
dest = p->screen_base + yy * p->fontheight * bytes + xx * 16;
cdat = p->fontdata + c * p->fontheight;
- fgx = attr_fgcol(p,conp);
- fgx = packed16_cmap[fgx];
- bgx = attr_bgcol(p,conp);
- bgx = packed16_cmap[bgx];
+ fgx = fbcon_cfb16_cmap[attr_fgcol(p, conp)];
+ bgx = fbcon_cfb16_cmap[attr_bgcol(p, conp)];
fgx |= (fgx << 16);
bgx |= (bgx << 16);
eorx = fgx ^ bgx;
for (rows = p->fontheight ; rows-- ; dest += bytes) {
- ((u_long *)dest)[0]= (tab_cfb16[*cdat >> 6] & eorx) ^ bgx;
- ((u_long *)dest)[1]= (tab_cfb16[*cdat >> 4 & 0x3] & eorx) ^ bgx;
- ((u_long *)dest)[2]= (tab_cfb16[*cdat >> 2 & 0x3] & eorx) ^ bgx;
- ((u_long *)dest)[3]= (tab_cfb16[*cdat++ & 0x3] & eorx) ^ bgx;
+ u8 bits = *cdat++;
+ ((u32 *)dest)[0] = (tab_cfb16[bits >> 6] & eorx) ^ bgx;
+ ((u32 *)dest)[1] = (tab_cfb16[bits >> 4 & 3] & eorx) ^ bgx;
+ ((u32 *)dest)[2] = (tab_cfb16[bits >> 2 & 3] & eorx) ^ bgx;
+ ((u32 *)dest)[3] = (tab_cfb16[bits & 3] & eorx) ^ bgx;
}
}
-static void putcs_cfb16(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx)
+void fbcon_cfb16_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
{
- u_char *cdat, c, *dest, *dest0;
- int rows,bytes=p->next_line;
- u_long eorx, fgx, bgx;
+ u8 *cdat, c, *dest, *dest0;
+ int rows, bytes = p->next_line;
+ u32 eorx, fgx, bgx;
dest0 = p->screen_base + yy * p->fontheight * bytes + xx * 16;
- fgx = attr_fgcol(p,conp);
- fgx = packed16_cmap[fgx];
- bgx = attr_bgcol(p,conp);
- bgx = packed16_cmap[bgx];
+ fgx = fbcon_cfb16_cmap[attr_fgcol(p, conp)];
+ bgx = fbcon_cfb16_cmap[attr_bgcol(p, conp)];
fgx |= (fgx << 16);
bgx |= (bgx << 16);
eorx = fgx ^ bgx;
@@ -184,49 +151,50 @@ static void putcs_cfb16(struct vc_data *conp, struct display *p, const char *s,
cdat = p->fontdata + c * p->fontheight;
for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
- ((u_long *)dest)[0]= (tab_cfb16[*cdat >> 6] & eorx) ^ bgx;
- ((u_long *)dest)[1]= (tab_cfb16[*cdat >> 4 & 0x3] & eorx) ^ bgx;
- ((u_long *)dest)[2]= (tab_cfb16[*cdat >> 2 & 0x3] & eorx) ^ bgx;
- ((u_long *)dest)[3]= (tab_cfb16[*cdat++ & 0x3] & eorx) ^ bgx;
+ u8 bits = *cdat++;
+ ((u32 *)dest)[0] = (tab_cfb16[bits >> 6] & eorx) ^ bgx;
+ ((u32 *)dest)[1] = (tab_cfb16[bits >> 4 & 3] & eorx) ^ bgx;
+ ((u32 *)dest)[2] = (tab_cfb16[bits >> 2 & 3] & eorx) ^ bgx;
+ ((u32 *)dest)[3] = (tab_cfb16[bits & 3] & eorx) ^ bgx;
}
- dest0+=16;
+ dest0 += 16;
}
}
-static void rev_char_cfb16(struct display *p, int xx, int yy)
+void fbcon_cfb16_revc(struct display *p, int xx, int yy)
{
- u_char *dest;
- int bytes=p->next_line, rows;
+ u8 *dest;
+ int bytes = p->next_line, rows;
dest = p->screen_base + yy * p->fontheight * bytes + xx * 16;
for (rows = p->fontheight ; rows-- ; dest += bytes) {
- ((u_long *)dest)[0] ^= 0xffffffff;
- ((u_long *)dest)[1] ^= 0xffffffff;
- ((u_long *)dest)[2] ^= 0xffffffff;
- ((u_long *)dest)[3] ^= 0xffffffff;
+ ((u32 *)dest)[0] ^= 0xffffffff;
+ ((u32 *)dest)[1] ^= 0xffffffff;
+ ((u32 *)dest)[2] ^= 0xffffffff;
+ ((u32 *)dest)[3] ^= 0xffffffff;
}
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_cfb16(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_cfb16, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_cfb16);
-}
-#endif /* MODULE */
+struct display_switch fbcon_cfb16 = {
+ fbcon_cfb16_setup, fbcon_cfb16_bmove, fbcon_cfb16_clear, fbcon_cfb16_putc,
+ fbcon_cfb16_putcs, fbcon_cfb16_revc
+};
/*
* Visible symbols for modules
*/
-EXPORT_SYMBOL(packed16_cmap);
+EXPORT_SYMBOL(fbcon_cfb16);
+EXPORT_SYMBOL(fbcon_cfb16_setup);
+EXPORT_SYMBOL(fbcon_cfb16_bmove);
+EXPORT_SYMBOL(fbcon_cfb16_clear);
+EXPORT_SYMBOL(fbcon_cfb16_putc);
+EXPORT_SYMBOL(fbcon_cfb16_putcs);
+EXPORT_SYMBOL(fbcon_cfb16_revc);
+EXPORT_SYMBOL(fbcon_cfb16_cmap);
diff --git a/drivers/video/fbcon-cfb16.h b/drivers/video/fbcon-cfb16.h
new file mode 100644
index 000000000..905d6329a
--- /dev/null
+++ b/drivers/video/fbcon-cfb16.h
@@ -0,0 +1,16 @@
+ /*
+ * 16 bpp packed pixel (cfb16)
+ */
+
+extern struct display_switch fbcon_cfb16;
+extern u16 fbcon_cfb16_cmap[16];
+extern void fbcon_cfb16_setup(struct display *p);
+extern void fbcon_cfb16_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width);
+extern void fbcon_cfb16_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_cfb16_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_cfb16_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_cfb16_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cfb2.c b/drivers/video/fbcon-cfb2.c
new file mode 100644
index 000000000..617c85235
--- /dev/null
+++ b/drivers/video/fbcon-cfb2.c
@@ -0,0 +1,205 @@
+/*
+ * linux/drivers/video/cfb2.c -- Low level frame buffer operations for 2 bpp
+ * packed pixels
+ *
+ * Created 26 Dec 1997 by Michael Schmitz
+ * Based on cfb4.c
+ *
+ * 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.
+ */
+
+#include <linux/module.h>
+#include <linux/tty.h>
+#include <linux/console.h>
+#include <linux/string.h>
+#include <linux/config.h>
+#include <linux/fb.h>
+
+#include "fbcon.h"
+#include "fbcon-cfb2.h"
+
+
+ /*
+ * 2 bpp packed pixels
+ */
+
+ /*
+ * IFF the font is even pixel aligned (that is to say each
+ * character start is a byte start in the pixel pairs). That
+ * avoids us having to mask bytes and means we won't be here
+ * all week. On a MacII that matters _lots_
+ */
+
+static u_char nibbletab_cfb2[]={
+ 0x00,0x03,0x0c,0x0f,
+ 0x30,0x33,0x3c,0x3f,
+ 0xc0,0xc3,0xcc,0xcf,
+ 0xf0,0xf3,0xfc,0xff
+};
+
+
+void fbcon_cfb2_setup(struct display *p)
+{
+ p->next_line = p->var.xres_virtual>>2;
+ p->next_plane = 0;
+}
+
+void fbcon_cfb2_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
+ u8 *src,*dst;
+
+ if (sx == 0 && dx == 0 && width * 2 == bytes) {
+ mymemmove(p->screen_base + dy * linesize,
+ p->screen_base + sy * linesize,
+ height * linesize);
+ }
+ else {
+ if (dy < sy || (dy == sy && dx < sx)) {
+ src = p->screen_base + sy * linesize + sx * 2;
+ dst = p->screen_base + dy * linesize + dx * 2;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 2);
+ src += bytes;
+ dst += bytes;
+ }
+ }
+ else {
+ src = p->screen_base + (sy+height) * linesize + sx * 2
+ - bytes;
+ dst = p->screen_base + (dy+height) * linesize + dx * 2
+ - bytes;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 2);
+ src -= bytes;
+ dst -= bytes;
+ }
+ }
+ }
+}
+
+void fbcon_cfb2_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
+{
+ u8 *dest0,*dest;
+ int bytes=p->next_line,lines=height * p->fontheight, rows, i;
+ u32 bgx;
+
+ dest = p->screen_base + sy * p->fontheight * bytes + sx * 2;
+
+ bgx=attr_bgcol_ec(p,conp);
+ bgx |= (bgx << 2); /* expand the colour to 16 bits */
+ bgx |= (bgx << 4);
+ bgx |= (bgx << 8);
+
+ if (sx == 0 && width * 2 == bytes) {
+ for (i = 0 ; i < lines * width ; i++) {
+ ((u16 *)dest)[0]=bgx;
+ dest+=2;
+ }
+ } else {
+ dest0=dest;
+ for (rows = lines; rows-- ; dest0 += bytes) {
+ dest=dest0;
+ for (i = 0 ; i < width ; i++) {
+ /* memset ?? */
+ ((u16 *)dest)[0]=bgx;
+ dest+=2;
+ }
+ }
+ }
+}
+
+void fbcon_cfb2_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
+{
+ u8 *dest,*cdat;
+ int bytes=p->next_line,rows;
+ u32 eorx,fgx,bgx;
+
+ c &= 0xff;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 2;
+ cdat = p->fontdata + c * p->fontheight;
+
+ fgx=3;/*attr_fgcol(p,conp)&0x0F;*/
+ bgx=attr_bgcol(p,conp)&0x0F;
+ fgx |= (fgx << 2); /* expand color to 8 bits */
+ fgx |= (fgx << 4);
+ bgx |= (bgx << 2);
+ bgx |= (bgx << 4);
+ eorx = fgx ^ bgx;
+
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ ((u8 *)dest)[0]=
+ (nibbletab_cfb2[*cdat >> 4] & eorx) ^ bgx;
+ ((u8 *)dest)[1]=
+ (nibbletab_cfb2[*cdat++ & 0xf] & eorx) ^ bgx;
+ }
+}
+
+void fbcon_cfb2_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
+{
+ u8 *cdat, c, *dest, *dest0;
+ int rows,bytes=p->next_line;
+ u32 eorx, fgx, bgx;
+
+ dest0 = p->screen_base + yy * p->fontheight * bytes + xx * 2;
+ fgx=3/*attr_fgcol(p,conp)*/;
+ bgx=attr_bgcol(p,conp);
+ fgx |= (fgx << 2);
+ fgx |= (fgx << 4);
+ bgx |= (bgx << 2);
+ bgx |= (bgx << 4);
+ eorx = fgx ^ bgx;
+ while (count--) {
+ c = *s++;
+ cdat = p->fontdata + c * p->fontheight;
+
+ for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
+ ((u8 *)dest)[0]=
+ (nibbletab_cfb2[*cdat >> 4] & eorx) ^ bgx;
+ ((u8 *)dest)[1]=
+ (nibbletab_cfb2[*cdat++ & 0xf] & eorx) ^ bgx;
+ }
+ dest0+=2;
+ }
+}
+
+void fbcon_cfb2_revc(struct display *p, int xx, int yy)
+{
+ u8 *dest;
+ int bytes=p->next_line, rows;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 2;
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ ((u16 *)dest)[0] ^= 0xffff;
+ }
+}
+
+
+ /*
+ * `switch' for the low level operations
+ */
+
+struct display_switch fbcon_cfb2 = {
+ fbcon_cfb2_setup, fbcon_cfb2_bmove, fbcon_cfb2_clear, fbcon_cfb2_putc,
+ fbcon_cfb2_putcs, fbcon_cfb2_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_cfb2);
+EXPORT_SYMBOL(fbcon_cfb2_setup);
+EXPORT_SYMBOL(fbcon_cfb2_bmove);
+EXPORT_SYMBOL(fbcon_cfb2_clear);
+EXPORT_SYMBOL(fbcon_cfb2_putc);
+EXPORT_SYMBOL(fbcon_cfb2_putcs);
+EXPORT_SYMBOL(fbcon_cfb2_revc);
diff --git a/drivers/video/fbcon-cfb2.h b/drivers/video/fbcon-cfb2.h
new file mode 100644
index 000000000..4fb3bb13a
--- /dev/null
+++ b/drivers/video/fbcon-cfb2.h
@@ -0,0 +1,15 @@
+ /*
+ * 2 bpp packed pixel (cfb2)
+ */
+
+extern struct display_switch fbcon_cfb2;
+extern void fbcon_cfb2_setup(struct display *p);
+extern void fbcon_cfb2_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_cfb2_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_cfb2_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_cfb2_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_cfb2_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cfb24.c b/drivers/video/fbcon-cfb24.c
new file mode 100644
index 000000000..65a4ad556
--- /dev/null
+++ b/drivers/video/fbcon-cfb24.c
@@ -0,0 +1,221 @@
+/*
+ * linux/drivers/video/cfb24.c -- Low level frame buffer operations for 24 bpp
+ * truecolor packed pixels
+ *
+ * Created 7 Mar 1998 by Geert Uytterhoeven
+ *
+ * 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.
+ */
+
+#include <linux/module.h>
+#include <linux/tty.h>
+#include <linux/console.h>
+#include <linux/string.h>
+#include <linux/config.h>
+#include <linux/fb.h>
+
+#include "fbcon.h"
+#include "fbcon-cfb24.h"
+
+
+#warning Remove this warning after the test cycle was finalized
+
+
+ /*
+ * 24 bpp packed pixels
+ */
+
+u32 fbcon_cfb24_cmap[16];
+
+void fbcon_cfb24_setup(struct display *p)
+{
+ p->next_line = p->line_length ? p->line_length : p->var.xres_virtual*3;
+ p->next_plane = 0;
+}
+
+void fbcon_cfb24_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
+ u8 *src, *dst;
+
+ if (sx == 0 && dx == 0 && width * 24 == bytes)
+ mymemmove(p->screen_base + dy * linesize,
+ p->screen_base + sy * linesize,
+ height * linesize);
+ else if (dy < sy || (dy == sy && dx < sx)) {
+ src = p->screen_base + sy * linesize + sx * 24;
+ dst = p->screen_base + dy * linesize + dx * 24;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 24);
+ src += bytes;
+ dst += bytes;
+ }
+ } else {
+ src = p->screen_base + (sy+height) * linesize + sx * 24 - bytes;
+ dst = p->screen_base + (dy+height) * linesize + dx * 24 - bytes;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 24);
+ src -= bytes;
+ dst -= bytes;
+ }
+ }
+}
+
+void fbcon_cfb24_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
+{
+ u8 *dest0, *dest;
+ int bytes = p->next_line, lines = height * p->fontheight, rows, i;
+ u32 bgx;
+
+ dest = p->screen_base + sy * p->fontheight * bytes + sx * 24;
+
+ bgx = fbcon_cfb24_cmap[attr_bgcol_ec(p, conp)];
+
+ if (sx == 0 && width * 24 == bytes)
+ for (i = 0 ; i < lines * width ; i++) {
+ ((u32 *)dest)[0] = bgx;
+ ((u32 *)dest)[1] = bgx;
+ ((u32 *)dest)[2] = bgx;
+ ((u32 *)dest)[3] = bgx;
+ ((u32 *)dest)[4] = bgx;
+ ((u32 *)dest)[5] = bgx;
+ dest += 24;
+ }
+ else {
+ dest0 = dest;
+ for (rows = lines; rows-- ; dest0 += bytes) {
+ dest = dest0;
+ for (i = 0 ; i < width ; i++) {
+ ((u32 *)dest)[0] = bgx;
+ ((u32 *)dest)[1] = bgx;
+ ((u32 *)dest)[2] = bgx;
+ ((u32 *)dest)[3] = bgx;
+ ((u32 *)dest)[4] = bgx;
+ ((u32 *)dest)[5] = bgx;
+ dest += 24;
+ }
+ }
+ }
+}
+
+static inline void store4pixels(u32 d1, u32 d2, u32 d3, u32 d4, u32 *dest)
+{
+#if defined(__BIG_ENDIAN)
+ *dest++ = (d1<<8) | (d2>>16);
+ *dest++ = (d2<<16) | (d3>>8);
+ *dest++ = (d3<<24) | d4;
+#elif defined(__LITTLE_ENDIAN)
+#error Please add support for little endian byteorder
+#else
+#error FIXME: No endianness??
+#endif
+}
+
+void fbcon_cfb24_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
+{
+ u8 *dest, *cdat;
+ int bytes = p->next_line, rows;
+ u32 eorx, fgx, bgx;
+
+ c &= 0xff;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 24;
+ cdat = p->fontdata + c * p->fontheight;
+
+ fgx = fbcon_cfb24_cmap[attr_fgcol(p, conp)];
+ bgx = fbcon_cfb24_cmap[attr_bgcol(p, conp)];
+ eorx = fgx ^ bgx;
+
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ u8 bits = *cdat++;
+ u32 d1, d2, d3, d4;
+ d1 = (-(bits >> 7) & eorx) ^ bgx;
+ d2 = (-(bits >> 6 & 1) & eorx) ^ bgx;
+ d3 = (-(bits >> 5 & 1) & eorx) ^ bgx;
+ d4 = (-(bits >> 4 & 1) & eorx) ^ bgx;
+ store4pixels(d1, d2, d3, d4, (u32 *)dest);
+ d1 = (-(bits >> 3 & 1) & eorx) ^ bgx;
+ d2 = (-(bits >> 2 & 1) & eorx) ^ bgx;
+ d3 = (-(bits >> 1 & 1) & eorx) ^ bgx;
+ d4 = (-(bits & 1) & eorx) ^ bgx;
+ store4pixels(d1, d2, d3, d4, (u32 *)(dest+12));
+ }
+}
+
+void fbcon_cfb24_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
+{
+ u8 *cdat, c, *dest, *dest0;
+ int rows, bytes = p->next_line;
+ u32 eorx, fgx, bgx;
+
+ dest0 = p->screen_base + yy * p->fontheight * bytes + xx * 24;
+ fgx = fbcon_cfb24_cmap[attr_fgcol(p, conp)];
+ bgx = fbcon_cfb24_cmap[attr_bgcol(p, conp)];
+ eorx = fgx ^ bgx;
+ while (count--) {
+ c = *s++;
+ cdat = p->fontdata + c * p->fontheight;
+
+ for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
+ u8 bits = *cdat++;
+ u32 d1, d2, d3, d4;
+ d1 = (-(bits >> 7) & eorx) ^ bgx;
+ d2 = (-(bits >> 6 & 1) & eorx) ^ bgx;
+ d3 = (-(bits >> 5 & 1) & eorx) ^ bgx;
+ d4 = (-(bits >> 4 & 1) & eorx) ^ bgx;
+ store4pixels(d1, d2, d3, d4, (u32 *)dest);
+ d1 = (-(bits >> 3 & 1) & eorx) ^ bgx;
+ d2 = (-(bits >> 2 & 1) & eorx) ^ bgx;
+ d3 = (-(bits >> 1 & 1) & eorx) ^ bgx;
+ d4 = (-(bits & 1) & eorx) ^ bgx;
+ store4pixels(d1, d2, d3, d4, (u32 *)(dest+12));
+ }
+ dest0 += 24;
+ }
+}
+
+void fbcon_cfb24_revc(struct display *p, int xx, int yy)
+{
+ u8 *dest;
+ int bytes = p->next_line, rows;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 24;
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ ((u32 *)dest)[0] ^= 0xffffffff;
+ ((u32 *)dest)[1] ^= 0xffffffff;
+ ((u32 *)dest)[2] ^= 0xffffffff;
+ ((u32 *)dest)[3] ^= 0xffffffff;
+ ((u32 *)dest)[4] ^= 0xffffffff;
+ ((u32 *)dest)[5] ^= 0xffffffff;
+ }
+}
+
+
+ /*
+ * `switch' for the low level operations
+ */
+
+struct display_switch fbcon_cfb24 = {
+ fbcon_cfb24_setup, fbcon_cfb24_bmove, fbcon_cfb24_clear, fbcon_cfb24_putc,
+ fbcon_cfb24_putcs, fbcon_cfb24_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_cfb24);
+EXPORT_SYMBOL(fbcon_cfb24_setup);
+EXPORT_SYMBOL(fbcon_cfb24_bmove);
+EXPORT_SYMBOL(fbcon_cfb24_clear);
+EXPORT_SYMBOL(fbcon_cfb24_putc);
+EXPORT_SYMBOL(fbcon_cfb24_putcs);
+EXPORT_SYMBOL(fbcon_cfb24_revc);
+EXPORT_SYMBOL(fbcon_cfb24_cmap);
diff --git a/drivers/video/fbcon-cfb24.h b/drivers/video/fbcon-cfb24.h
new file mode 100644
index 000000000..bd672ab20
--- /dev/null
+++ b/drivers/video/fbcon-cfb24.h
@@ -0,0 +1,16 @@
+ /*
+ * 24 bpp packed pixel (cfb24)
+ */
+
+extern struct display_switch fbcon_cfb24;
+extern u32 fbcon_cfb24_cmap[16];
+extern void fbcon_cfb24_setup(struct display *p);
+extern void fbcon_cfb24_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width);
+extern void fbcon_cfb24_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_cfb24_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_cfb24_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_cfb24_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cfb32.c b/drivers/video/fbcon-cfb32.c
new file mode 100644
index 000000000..8c3306458
--- /dev/null
+++ b/drivers/video/fbcon-cfb32.c
@@ -0,0 +1,205 @@
+/*
+ * linux/drivers/video/cfb32.c -- Low level frame buffer operations for 32 bpp
+ * truecolor packed pixels
+ *
+ * Created 28 Dec 1997 by Geert Uytterhoeven
+ *
+ * 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.
+ */
+
+#include <linux/module.h>
+#include <linux/tty.h>
+#include <linux/console.h>
+#include <linux/string.h>
+#include <linux/config.h>
+#include <linux/fb.h>
+
+#include "fbcon.h"
+#include "fbcon-cfb32.h"
+
+
+ /*
+ * 32 bpp packed pixels
+ */
+
+u32 fbcon_cfb32_cmap[16];
+
+void fbcon_cfb32_setup(struct display *p)
+{
+ p->next_line = p->line_length ? p->line_length : p->var.xres_virtual<<2;
+ p->next_plane = 0;
+}
+
+void fbcon_cfb32_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
+ u8 *src, *dst;
+
+ if (sx == 0 && dx == 0 && width * 32 == bytes)
+ mymemmove(p->screen_base + dy * linesize,
+ p->screen_base + sy * linesize,
+ height * linesize);
+ else if (dy < sy || (dy == sy && dx < sx)) {
+ src = p->screen_base + sy * linesize + sx * 32;
+ dst = p->screen_base + dy * linesize + dx * 32;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 32);
+ src += bytes;
+ dst += bytes;
+ }
+ } else {
+ src = p->screen_base + (sy+height) * linesize + sx * 32 - bytes;
+ dst = p->screen_base + (dy+height) * linesize + dx * 32 - bytes;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 32);
+ src -= bytes;
+ dst -= bytes;
+ }
+ }
+}
+
+void fbcon_cfb32_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
+{
+ u8 *dest0, *dest;
+ int bytes = p->next_line, lines = height * p->fontheight, rows, i;
+ u32 bgx;
+
+ dest = p->screen_base + sy * p->fontheight * bytes + sx * 32;
+
+ bgx = fbcon_cfb32_cmap[attr_bgcol_ec(p, conp)];
+
+ if (sx == 0 && width * 32 == bytes)
+ for (i = 0 ; i < lines * width ; i++) {
+ ((u32 *)dest)[0] = bgx;
+ ((u32 *)dest)[1] = bgx;
+ ((u32 *)dest)[2] = bgx;
+ ((u32 *)dest)[3] = bgx;
+ ((u32 *)dest)[4] = bgx;
+ ((u32 *)dest)[5] = bgx;
+ ((u32 *)dest)[6] = bgx;
+ ((u32 *)dest)[7] = bgx;
+ dest += 32;
+ }
+ else {
+ dest0 = dest;
+ for (rows = lines; rows-- ; dest0 += bytes) {
+ dest = dest0;
+ for (i = 0 ; i < width ; i++) {
+ ((u32 *)dest)[0] = bgx;
+ ((u32 *)dest)[1] = bgx;
+ ((u32 *)dest)[2] = bgx;
+ ((u32 *)dest)[3] = bgx;
+ ((u32 *)dest)[4] = bgx;
+ ((u32 *)dest)[5] = bgx;
+ ((u32 *)dest)[6] = bgx;
+ ((u32 *)dest)[7] = bgx;
+ dest += 32;
+ }
+ }
+ }
+}
+
+void fbcon_cfb32_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
+{
+ u8 *dest, *cdat;
+ int bytes = p->next_line, rows;
+ u32 eorx, fgx, bgx;
+
+ c &= 0xff;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 32;
+ cdat = p->fontdata + c * p->fontheight;
+
+ fgx = fbcon_cfb32_cmap[attr_fgcol(p, conp)];
+ bgx = fbcon_cfb32_cmap[attr_bgcol(p, conp)];
+ eorx = fgx ^ bgx;
+
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ u8 bits = *cdat++;
+ ((u32 *)dest)[0] = (-(bits >> 7) & eorx) ^ bgx;
+ ((u32 *)dest)[1] = (-(bits >> 6 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[2] = (-(bits >> 5 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[3] = (-(bits >> 4 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[4] = (-(bits >> 3 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[5] = (-(bits >> 2 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[6] = (-(bits >> 1 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[7] = (-(bits & 1) & eorx) ^ bgx;
+ }
+}
+
+void fbcon_cfb32_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
+{
+ u8 *cdat, c, *dest, *dest0;
+ int rows, bytes = p->next_line;
+ u32 eorx, fgx, bgx;
+
+ dest0 = p->screen_base + yy * p->fontheight * bytes + xx * 32;
+ fgx = fbcon_cfb32_cmap[attr_fgcol(p, conp)];
+ bgx = fbcon_cfb32_cmap[attr_bgcol(p, conp)];
+ eorx = fgx ^ bgx;
+ while (count--) {
+ c = *s++;
+ cdat = p->fontdata + c * p->fontheight;
+
+ for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
+ u8 bits = *cdat++;
+ ((u32 *)dest)[0] = (-(bits >> 7) & eorx) ^ bgx;
+ ((u32 *)dest)[1] = (-(bits >> 6 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[2] = (-(bits >> 5 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[3] = (-(bits >> 4 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[4] = (-(bits >> 3 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[5] = (-(bits >> 2 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[6] = (-(bits >> 1 & 1) & eorx) ^ bgx;
+ ((u32 *)dest)[7] = (-(bits & 1) & eorx) ^ bgx;
+ }
+ dest0 += 32;
+ }
+}
+
+void fbcon_cfb32_revc(struct display *p, int xx, int yy)
+{
+ u8 *dest;
+ int bytes = p->next_line, rows;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 32;
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ ((u32 *)dest)[0] ^= 0xffffffff;
+ ((u32 *)dest)[1] ^= 0xffffffff;
+ ((u32 *)dest)[2] ^= 0xffffffff;
+ ((u32 *)dest)[3] ^= 0xffffffff;
+ ((u32 *)dest)[4] ^= 0xffffffff;
+ ((u32 *)dest)[5] ^= 0xffffffff;
+ ((u32 *)dest)[6] ^= 0xffffffff;
+ ((u32 *)dest)[7] ^= 0xffffffff;
+ }
+}
+
+
+ /*
+ * `switch' for the low level operations
+ */
+
+struct display_switch fbcon_cfb32 = {
+ fbcon_cfb32_setup, fbcon_cfb32_bmove, fbcon_cfb32_clear, fbcon_cfb32_putc,
+ fbcon_cfb32_putcs, fbcon_cfb32_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_cfb32);
+EXPORT_SYMBOL(fbcon_cfb32_setup);
+EXPORT_SYMBOL(fbcon_cfb32_bmove);
+EXPORT_SYMBOL(fbcon_cfb32_clear);
+EXPORT_SYMBOL(fbcon_cfb32_putc);
+EXPORT_SYMBOL(fbcon_cfb32_putcs);
+EXPORT_SYMBOL(fbcon_cfb32_revc);
+EXPORT_SYMBOL(fbcon_cfb32_cmap);
diff --git a/drivers/video/fbcon-cfb32.h b/drivers/video/fbcon-cfb32.h
new file mode 100644
index 000000000..1f74141c2
--- /dev/null
+++ b/drivers/video/fbcon-cfb32.h
@@ -0,0 +1,16 @@
+ /*
+ * 32 bpp packed pixel (cfb32)
+ */
+
+extern struct display_switch fbcon_cfb32;
+extern u32 fbcon_cfb32_cmap[16];
+extern void fbcon_cfb32_setup(struct display *p);
+extern void fbcon_cfb32_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width);
+extern void fbcon_cfb32_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_cfb32_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_cfb32_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_cfb32_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cfb4.c b/drivers/video/fbcon-cfb4.c
new file mode 100644
index 000000000..bcdfcc436
--- /dev/null
+++ b/drivers/video/fbcon-cfb4.c
@@ -0,0 +1,208 @@
+/*
+ * linux/drivers/video/cfb4.c -- Low level frame buffer operations for 4 bpp
+ * packed pixels
+ *
+ * Created 26 Dec 1997 by Michael Schmitz
+ * Based on the old macfb.c 4bpp code by Alan Cox
+ *
+ * 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.
+ */
+
+#include <linux/module.h>
+#include <linux/tty.h>
+#include <linux/console.h>
+#include <linux/string.h>
+#include <linux/config.h>
+#include <linux/fb.h>
+
+#include "fbcon.h"
+#include "fbcon-cfb4.h"
+
+
+ /*
+ * 4 bpp packed pixels
+ */
+
+ /*
+ * IFF the font is even pixel aligned (that is to say each
+ * character start is a byte start in the pixel pairs). That
+ * avoids us having to mask bytes and means we won't be here
+ * all week. On a MacII that matters _lots_
+ */
+
+static u16 nibbletab_cfb4[] = {
+ 0x0000,0x000f,0x00f0,0x00ff,
+ 0x0f00,0x0f0f,0x0ff0,0x0fff,
+ 0xf000,0xf00f,0xf0f0,0xf0ff,
+ 0xff00,0xff0f,0xfff0,0xffff
+};
+
+void fbcon_cfb4_setup(struct display *p)
+{
+ p->next_line = p->var.xres_virtual>>1;
+ p->next_plane = 0;
+}
+
+void fbcon_cfb4_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
+ u8 *src,*dst;
+
+ if (sx == 0 && dx == 0 && width * 4 == bytes) {
+ mymemmove(p->screen_base + dy * linesize,
+ p->screen_base + sy * linesize,
+ height * linesize);
+ }
+ else {
+ if (dy < sy || (dy == sy && dx < sx)) {
+ src = p->screen_base + sy * linesize + sx * 4;
+ dst = p->screen_base + dy * linesize + dx * 4;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 4);
+ src += bytes;
+ dst += bytes;
+ }
+ }
+ else {
+ src = p->screen_base + (sy+height) * linesize + sx * 4
+ - bytes;
+ dst = p->screen_base + (dy+height) * linesize + dx * 4
+ - bytes;
+ for (rows = height * p->fontheight ; rows-- ;) {
+ mymemmove(dst, src, width * 4);
+ src -= bytes;
+ dst -= bytes;
+ }
+ }
+ }
+}
+
+void fbcon_cfb4_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
+{
+ u8 *dest0,*dest;
+ int bytes=p->next_line,lines=height * p->fontheight, rows, i;
+ u32 bgx;
+
+/* if(p->screen_base!=0xFDD00020)
+ mac_boom(1);*/
+ dest = p->screen_base + sy * p->fontheight * bytes + sx * 4;
+
+ bgx=attr_bgcol_ec(p,conp);
+ bgx |= (bgx << 4); /* expand the colour to 32bits */
+ bgx |= (bgx << 8);
+ bgx |= (bgx << 16);
+
+ if (sx == 0 && width * 4 == bytes) {
+ for (i = 0 ; i < lines * width ; i++) {
+ ((u32 *)dest)[0]=bgx;
+ dest+=4;
+ }
+ } else {
+ dest0=dest;
+ for (rows = lines; rows-- ; dest0 += bytes) {
+ dest=dest0;
+ for (i = 0 ; i < width ; i++) {
+ /* memset ?? */
+ ((u32 *)dest)[0]=bgx;
+ dest+=4;
+ }
+ }
+ }
+}
+
+void fbcon_cfb4_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
+{
+ u8 *dest,*cdat;
+ int bytes=p->next_line,rows;
+ u32 eorx,fgx,bgx;
+
+ c &= 0xff;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 4;
+ cdat = p->fontdata + c * p->fontheight;
+
+ fgx=15;/*attr_fgcol(p,conp)&0x0F;*/
+ bgx=attr_bgcol(p,conp)&0x0F;
+ fgx |= (fgx << 4);
+ fgx |= (fgx << 8);
+ bgx |= (bgx << 4);
+ bgx |= (bgx << 8);
+ eorx = fgx ^ bgx;
+
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ ((u16 *)dest)[0]=
+ (nibbletab_cfb4[*cdat >> 4] & eorx) ^ bgx;
+ ((u16 *)dest)[1]=
+ (nibbletab_cfb4[*cdat++ & 0xf] & eorx) ^ bgx;
+ }
+}
+
+void fbcon_cfb4_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
+{
+ u8 *cdat, c, *dest, *dest0;
+ int rows,bytes=p->next_line;
+ u32 eorx, fgx, bgx;
+
+ dest0 = p->screen_base + yy * p->fontheight * bytes + xx * 4;
+ fgx=15/*attr_fgcol(p,conp)*/;
+ bgx=attr_bgcol(p,conp);
+ fgx |= (fgx << 4);
+ fgx |= (fgx << 8);
+ fgx |= (fgx << 16);
+ bgx |= (bgx << 4);
+ bgx |= (bgx << 8);
+ bgx |= (bgx << 16);
+ eorx = fgx ^ bgx;
+ while (count--) {
+ c = *s++;
+ cdat = p->fontdata + c * p->fontheight;
+
+ for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
+ ((u16 *)dest)[0]=
+ (nibbletab_cfb4[*cdat >> 4] & eorx) ^ bgx;
+ ((u16 *)dest)[1]=
+ (nibbletab_cfb4[*cdat++ & 0xf] & eorx) ^ bgx;
+ }
+ dest0+=4;
+ }
+}
+
+void fbcon_cfb4_revc(struct display *p, int xx, int yy)
+{
+ u8 *dest;
+ int bytes=p->next_line, rows;
+
+ dest = p->screen_base + yy * p->fontheight * bytes + xx * 4;
+ for (rows = p->fontheight ; rows-- ; dest += bytes) {
+ ((u32 *)dest)[0] ^= 0x0f0f0f0f;
+ }
+}
+
+
+ /*
+ * `switch' for the low level operations
+ */
+
+struct display_switch fbcon_cfb4 = {
+ fbcon_cfb4_setup, fbcon_cfb4_bmove, fbcon_cfb4_clear, fbcon_cfb4_putc,
+ fbcon_cfb4_putcs, fbcon_cfb4_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_cfb4);
+EXPORT_SYMBOL(fbcon_cfb4_setup);
+EXPORT_SYMBOL(fbcon_cfb4_bmove);
+EXPORT_SYMBOL(fbcon_cfb4_clear);
+EXPORT_SYMBOL(fbcon_cfb4_putc);
+EXPORT_SYMBOL(fbcon_cfb4_putcs);
+EXPORT_SYMBOL(fbcon_cfb4_revc);
diff --git a/drivers/video/fbcon-cfb4.h b/drivers/video/fbcon-cfb4.h
new file mode 100644
index 000000000..6fe3bc5a4
--- /dev/null
+++ b/drivers/video/fbcon-cfb4.h
@@ -0,0 +1,15 @@
+ /*
+ * 4 bpp packed pixel (cfb4)
+ */
+
+extern struct display_switch fbcon_cfb4;
+extern void fbcon_cfb4_setup(struct display *p);
+extern void fbcon_cfb4_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_cfb4_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_cfb4_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_cfb4_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_cfb4_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cfb8.c b/drivers/video/fbcon-cfb8.c
index 5fa339be1..c559f4025 100644
--- a/drivers/video/fbcon-cfb8.c
+++ b/drivers/video/fbcon-cfb8.c
@@ -13,70 +13,44 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
#include "fbcon.h"
-
-
- /*
- * Prototypes
- */
-
-static int open_cfb8(struct display *p);
-static void release_cfb8(void);
-static void bmove_cfb8(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_cfb8(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width);
-static void putc_cfb8(struct vc_data *conp, struct display *p, int c, int yy,
- int xx);
-static void putcs_cfb8(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx);
-static void rev_char_cfb8(struct display *p, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_cfb8 = {
- open_cfb8, release_cfb8, bmove_cfb8, clear_cfb8, putc_cfb8, putcs_cfb8,
- rev_char_cfb8
-};
+#include "fbcon-cfb8.h"
/*
* 8 bpp packed pixels
*/
-static u_long nibbletab_cfb8[] = {
+static u32 nibbletab_cfb8[] = {
+#if defined(__BIG_ENDIAN)
0x00000000,0x000000ff,0x0000ff00,0x0000ffff,
0x00ff0000,0x00ff00ff,0x00ffff00,0x00ffffff,
0xff000000,0xff0000ff,0xff00ff00,0xff00ffff,
0xffff0000,0xffff00ff,0xffffff00,0xffffffff
+#elif defined(__LITTLE_ENDIAN)
+ 0x00000000,0xff000000,0x00ff0000,0xffff0000,
+ 0x0000ff00,0xff00ff00,0x00ffff00,0xffffff00,
+ 0x000000ff,0xff0000ff,0x00ff00ff,0xffff00ff,
+ 0x0000ffff,0xff00ffff,0x00ffffff,0xffffffff
+#else
+#error FIXME: No endianness??
+#endif
};
-static int open_cfb8(struct display *p)
+void fbcon_cfb8_setup(struct display *p)
{
- if (p->type != FB_TYPE_PACKED_PIXELS || p->var.bits_per_pixel != 8)
- return -EINVAL;
-
p->next_line = p->var.xres_virtual;
p->next_plane = 0;
- MOD_INC_USE_COUNT;
- return 0;
}
-static void release_cfb8(void)
-{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_cfb8(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
+void fbcon_cfb8_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
- u_char *src,*dst;
+ u8 *src,*dst;
if (sx == 0 && dx == 0 && width * 8 == bytes)
mymemmove(p->screen_base + dy * linesize,
@@ -101,12 +75,12 @@ static void bmove_cfb8(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_cfb8(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width)
+void fbcon_cfb8_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
{
- u_char *dest0,*dest;
+ u8 *dest0,*dest;
int bytes=p->next_line,lines=height * p->fontheight, rows, i;
- u_long bgx;
+ u32 bgx;
dest = p->screen_base + sy * p->fontheight * bytes + sx * 8;
@@ -116,8 +90,8 @@ static void clear_cfb8(struct vc_data *conp, struct display *p, int sy, int sx,
if (sx == 0 && width * 8 == bytes)
for (i = 0 ; i < lines * width ; i++) {
- ((u_long *)dest)[0]=bgx;
- ((u_long *)dest)[1]=bgx;
+ ((u32 *)dest)[0]=bgx;
+ ((u32 *)dest)[1]=bgx;
dest+=8;
}
else {
@@ -125,20 +99,20 @@ static void clear_cfb8(struct vc_data *conp, struct display *p, int sy, int sx,
for (rows = lines; rows-- ; dest0 += bytes) {
dest=dest0;
for (i = 0 ; i < width ; i++) {
- ((u_long *)dest)[0]=bgx;
- ((u_long *)dest)[1]=bgx;
+ ((u32 *)dest)[0]=bgx;
+ ((u32 *)dest)[1]=bgx;
dest+=8;
}
}
}
}
-static void putc_cfb8(struct vc_data *conp, struct display *p, int c, int yy,
- int xx)
+void fbcon_cfb8_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
{
- u_char *dest,*cdat;
+ u8 *dest,*cdat;
int bytes=p->next_line,rows;
- ulong eorx,fgx,bgx;
+ u32 eorx,fgx,bgx;
c &= 0xff;
@@ -154,17 +128,17 @@ static void putc_cfb8(struct vc_data *conp, struct display *p, int c, int yy,
eorx = fgx ^ bgx;
for (rows = p->fontheight ; rows-- ; dest += bytes) {
- ((u_long *)dest)[0]= (nibbletab_cfb8[*cdat >> 4] & eorx) ^ bgx;
- ((u_long *)dest)[1]= (nibbletab_cfb8[*cdat++ & 0xf] & eorx) ^ bgx;
+ ((u32 *)dest)[0]= (nibbletab_cfb8[*cdat >> 4] & eorx) ^ bgx;
+ ((u32 *)dest)[1]= (nibbletab_cfb8[*cdat++ & 0xf] & eorx) ^ bgx;
}
}
-static void putcs_cfb8(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx)
+void fbcon_cfb8_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
{
- u_char *cdat, c, *dest, *dest0;
+ u8 *cdat, c, *dest, *dest0;
int rows,bytes=p->next_line;
- u_long eorx, fgx, bgx;
+ u32 eorx, fgx, bgx;
dest0 = p->screen_base + yy * p->fontheight * bytes + xx * 8;
fgx=attr_fgcol(p,conp);
@@ -179,39 +153,44 @@ static void putcs_cfb8(struct vc_data *conp, struct display *p, const char *s,
cdat = p->fontdata + c * p->fontheight;
for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
- ((u_long *)dest)[0]= (nibbletab_cfb8[*cdat >> 4] & eorx) ^ bgx;
- ((u_long *)dest)[1]= (nibbletab_cfb8[*cdat++ & 0xf] & eorx) ^
- bgx;
+ ((u32 *)dest)[0]= (nibbletab_cfb8[*cdat >> 4] & eorx) ^ bgx;
+ ((u32 *)dest)[1]= (nibbletab_cfb8[*cdat++ & 0xf] & eorx) ^ bgx;
}
dest0+=8;
}
}
-static void rev_char_cfb8(struct display *p, int xx, int yy)
+void fbcon_cfb8_revc(struct display *p, int xx, int yy)
{
- u_char *dest;
+ u8 *dest;
int bytes=p->next_line, rows;
dest = p->screen_base + yy * p->fontheight * bytes + xx * 8;
for (rows = p->fontheight ; rows-- ; dest += bytes) {
- ((u_long *)dest)[0] ^= 0x0f0f0f0f;
- ((u_long *)dest)[1] ^= 0x0f0f0f0f;
+ ((u32 *)dest)[0] ^= 0x0f0f0f0f;
+ ((u32 *)dest)[1] ^= 0x0f0f0f0f;
}
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_cfb8(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_cfb8, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_cfb8);
-}
-#endif /* MODULE */
+struct display_switch fbcon_cfb8 = {
+ fbcon_cfb8_setup, fbcon_cfb8_bmove, fbcon_cfb8_clear, fbcon_cfb8_putc,
+ fbcon_cfb8_putcs, fbcon_cfb8_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_cfb8);
+EXPORT_SYMBOL(fbcon_cfb8_setup);
+EXPORT_SYMBOL(fbcon_cfb8_bmove);
+EXPORT_SYMBOL(fbcon_cfb8_clear);
+EXPORT_SYMBOL(fbcon_cfb8_putc);
+EXPORT_SYMBOL(fbcon_cfb8_putcs);
+EXPORT_SYMBOL(fbcon_cfb8_revc);
diff --git a/drivers/video/fbcon-cfb8.h b/drivers/video/fbcon-cfb8.h
new file mode 100644
index 000000000..4c0ffec99
--- /dev/null
+++ b/drivers/video/fbcon-cfb8.h
@@ -0,0 +1,15 @@
+ /*
+ * 8 bpp packed pixel (cfb8)
+ */
+
+extern struct display_switch fbcon_cfb8;
+extern void fbcon_cfb8_setup(struct display *p);
+extern void fbcon_cfb8_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_cfb8_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_cfb8_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_cfb8_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_cfb8_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-cyber.c b/drivers/video/fbcon-cyber.c
deleted file mode 100644
index ee740516d..000000000
--- a/drivers/video/fbcon-cyber.c
+++ /dev/null
@@ -1,229 +0,0 @@
-/*
- * linux/drivers/video/cyber.c -- Low level frame buffer operations for the
- * CyberVision64 (accelerated)
- *
- * Created 5 Apr 1997 by Geert Uytterhoeven
- *
- * 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.
- */
-
-#include <linux/module.h>
-#include <linux/tty.h>
-#include <linux/console.h>
-#include <linux/string.h>
-#include <linux/fb.h>
-
-#include "fbcon.h"
-#include "s3blit.h"
-
-
- /*
- * Prototypes
- */
-
-static int open_cyber(struct display *p);
-static void release_cyber(void);
-static void bmove_cyber(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_cyber(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width);
-static void putc_cyber(struct vc_data *conp, struct display *p, int c, int yy,
- int xx);
-static void putcs_cyber(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx);
-static void rev_char_cyber(struct display *p, int xx, int yy);
-
-
- /*
- * Acceleration functions in cyberfb.c
- */
-
-extern void Cyber_WaitQueue(unsigned short fifo);
-extern void Cyber_WaitBlit(void);
-extern void Cyber_BitBLT(unsigned short curx, unsigned short cury,
- unsigned short destx, unsigned short desty,
- unsigned short width, unsigned short height,
- unsigned short mode);
-extern void Cyber_RectFill(unsigned short xx, unsigned short yy,
- unsigned short width, unsigned short height,
- unsigned short mode, unsigned short fillcolor);
-extern void Cyber_MoveCursor(unsigned short xx, unsigned short yy);
-
-
- /*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_cyber = {
- open_cyber, release_cyber, bmove_cyber, clear_cyber, putc_cyber,
- putcs_cyber, rev_char_cyber
-};
-
-
- /*
- * CyberVision64 (accelerated)
- */
-
-static int open_cyber(struct display *p)
-{
- if (p->type != FB_TYPE_PACKED_PIXELS ||
- p->var.accel != FB_ACCEL_CYBERVISION)
- return -EINVAL;
-
- p->next_line = p->var.xres_virtual*p->var.bits_per_pixel>>3;
- p->next_plane = 0;
- MOD_INC_USE_COUNT;
- return 0;
-}
-
-static void release_cyber(void)
-{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_cyber(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
-{
- sx *= 8; dx *= 8; width *= 8;
- Cyber_BitBLT((u_short)sx, (u_short)(sy*p->fontheight), (u_short)dx,
- (u_short)(dy*p->fontheight), (u_short)width,
- (u_short)(height*p->fontheight), (u_short)S3_NEW);
-}
-
-static void clear_cyber(struct vc_data *conp, struct display *p, int
- sy, int sx, int height, int width)
-{
- unsigned char bg;
-
- sx *= 8; width *= 8;
- bg = attr_bgcol_ec(p,conp);
- Cyber_RectFill((u_short)sx,
- (u_short)(sy*p->fontheight),
- (u_short)width,
- (u_short)(height*p->fontheight),
- (u_short)S3_NEW,
- (u_short)bg);
-}
-
-static void putc_cyber(struct vc_data *conp, struct display *p, int c, int yy,
- int xx)
-{
- u_char *dest, *cdat;
- u_long tmp;
- u_int rows, revs, underl;
- u_char d;
- u_char fg, bg;
-
- c &= 0xff;
-
- dest = p->screen_base+yy*p->fontheight*p->next_line+8*xx;
- cdat = p->fontdata+(c*p->fontheight);
- fg = p->fgcol;
- bg = p->bgcol;
- revs = conp->vc_reverse;
- underl = conp->vc_underline;
-
- Cyber_WaitBlit();
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat++;
-
- if (underl && !rows)
- d = 0xff;
- if (revs)
- d = ~d;
-
- tmp = ((d & 0x80) ? fg : bg) << 24;
- tmp |= ((d & 0x40) ? fg : bg) << 16;
- tmp |= ((d & 0x20) ? fg : bg) << 8;
- tmp |= ((d & 0x10) ? fg : bg);
- *((u_long*) dest) = tmp;
- tmp = ((d & 0x8) ? fg : bg) << 24;
- tmp |= ((d & 0x4) ? fg : bg) << 16;
- tmp |= ((d & 0x2) ? fg : bg) << 8;
- tmp |= ((d & 0x1) ? fg : bg);
- *((u_long*) dest + 1) = tmp;
- }
-}
-
-static void putcs_cyber(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx)
-{
- u_char *dest, *dest0, *cdat;
- u_long tmp;
- u_int rows, underl;
- u_char c, d;
- u_char fg, bg;
-
- dest0 = p->screen_base+yy*p->fontheight*p->next_line+8*xx;
- fg = p->fgcol;
- bg = p->bgcol;
- underl = conp->vc_underline;
-
- Cyber_WaitBlit();
- while (count--) {
- c = *s++;
- dest = dest0;
- dest0 += 8;
- cdat = p->fontdata+(c*p->fontheight);
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat++;
-
- if (underl && !rows)
- d = 0xff;
-
- tmp = ((d & 0x80) ? fg : bg) << 24;
- tmp |= ((d & 0x40) ? fg : bg) << 16;
- tmp |= ((d & 0x20) ? fg : bg) << 8;
- tmp |= ((d & 0x10) ? fg : bg);
- *((u_long*) dest) = tmp;
- tmp = ((d & 0x8) ? fg : bg) << 24;
- tmp |= ((d & 0x4) ? fg : bg) << 16;
- tmp |= ((d & 0x2) ? fg : bg) << 8;
- tmp |= ((d & 0x1) ? fg : bg);
- *((u_long*) dest + 1) = tmp;
- }
- }
-}
-
-
-static void rev_char_cyber(struct display *p, int xx, int yy)
-{
- unsigned char *dest;
- unsigned int rows;
- unsigned char fg, bg;
-
- fg = p->fgcol;
- bg = p->bgcol;
-
- dest = p->screen_base+yy*p->fontheight*p->next_line+8*xx;
- Cyber_WaitBlit();
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- *dest = (*dest == fg) ? bg : fg;
- *(dest+1) = (*(dest + 1) == fg) ? bg : fg;
- *(dest+2) = (*(dest + 2) == fg) ? bg : fg;
- *(dest+3) = (*(dest + 3) == fg) ? bg : fg;
- *(dest+4) = (*(dest + 4) == fg) ? bg : fg;
- *(dest+5) = (*(dest + 5) == fg) ? bg : fg;
- *(dest+6) = (*(dest + 6) == fg) ? bg : fg;
- *(dest+7) = (*(dest + 7) == fg) ? bg : fg;
- }
-}
-
-
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_cyber(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_cyber, 1));
-}
-
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_cyber);
-}
-#endif /* MODULE */
diff --git a/drivers/video/fbcon-ilbm.c b/drivers/video/fbcon-ilbm.c
index 33be946e2..82f9982f6 100644
--- a/drivers/video/fbcon-ilbm.c
+++ b/drivers/video/fbcon-ilbm.c
@@ -16,33 +16,7 @@
#include <linux/fb.h>
#include "fbcon.h"
-
-
- /*
- * Prototypes
- */
-
-static int open_ilbm(struct display *p);
-static void release_ilbm(void);
-static void bmove_ilbm(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_ilbm(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width);
-static void putc_ilbm(struct vc_data *conp, struct display *p, int c, int yy,
- int xx);
-static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx);
-static void rev_char_ilbm(struct display *p, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_ilbm = {
- open_ilbm, release_ilbm, bmove_ilbm, clear_ilbm, putc_ilbm, putcs_ilbm,
- rev_char_ilbm
-};
+#include "fbcon-ilbm.h"
/*
@@ -56,11 +30,8 @@ static struct display_switch dispsw_ilbm = {
* much performance loss?
*/
-static int open_ilbm(struct display *p)
+void fbcon_ilbm_setup(struct display *p)
{
- if (p->type != FB_TYPE_INTERLEAVED_PLANES || p->type_aux == 2)
- return -EINVAL;
-
if (p->line_length) {
p->next_line = p->line_length*p->var.bits_per_pixel;
p->next_plane = p->line_length;
@@ -68,24 +39,17 @@ static int open_ilbm(struct display *p)
p->next_line = p->type_aux;
p->next_plane = p->type_aux/p->var.bits_per_pixel;
}
- MOD_INC_USE_COUNT;
- return 0;
}
-static void release_ilbm(void)
-{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_ilbm(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
+void fbcon_ilbm_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
if (sx == 0 && dx == 0 && width == p->next_plane)
mymemmove(p->screen_base+dy*p->fontheight*p->next_line,
p->screen_base+sy*p->fontheight*p->next_line,
height*p->fontheight*p->next_line);
else {
- u_char *src, *dest;
+ u8 *src, *dest;
u_int i;
if (dy <= sy) {
@@ -108,10 +72,10 @@ static void bmove_ilbm(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_ilbm(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width)
+void fbcon_ilbm_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
{
- u_char *dest;
+ u8 *dest;
u_int i, rows;
int bg, bg0;
@@ -130,12 +94,12 @@ static void clear_ilbm(struct vc_data *conp, struct display *p, int sy, int sx,
}
}
-static void putc_ilbm(struct vc_data *conp, struct display *p, int c, int yy,
- int xx)
+void fbcon_ilbm_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
{
- u_char *dest, *cdat;
+ u8 *dest, *cdat;
u_int rows, i;
- u_char d;
+ u8 d;
int fg0, bg0, fg, bg;
c &= 0xff;
@@ -150,16 +114,17 @@ static void putc_ilbm(struct vc_data *conp, struct display *p, int c, int yy,
fg = fg0;
bg = bg0;
for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
- if (bg & 1)
+ if (bg & 1){
if (fg & 1)
*dest = 0xff;
else
*dest = ~d;
- else
+ }else{
if (fg & 1)
*dest = d;
else
*dest = 0x00;
+ }
bg >>= 1;
fg >>= 1;
}
@@ -181,13 +146,13 @@ static void putc_ilbm(struct vc_data *conp, struct display *p, int c, int yy,
* -- Geert
*/
-static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx)
+void fbcon_ilbm_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
{
- u_char *dest0, *dest, *cdat1, *cdat2, *cdat3, *cdat4;
+ u8 *dest0, *dest, *cdat1, *cdat2, *cdat3, *cdat4;
u_int rows, i;
- u_char c1, c2, c3, c4;
- u_long d;
+ u8 c1, c2, c3, c4;
+ u32 d;
int fg0, bg0, fg, bg;
dest0 = p->screen_base+yy*p->fontheight*p->next_line+xx;
@@ -206,16 +171,17 @@ static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
fg = fg0;
bg = bg0;
for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
- if (bg & 1)
+ if (bg & 1){
if (fg & 1)
*dest = 0xff;
else
*dest = ~d;
- else
+ }else{
if (fg & 1)
*dest = d;
else
*dest = 0x00;
+ }
bg >>= 1;
fg >>= 1;
}
@@ -232,20 +198,27 @@ static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
cdat3 = p->fontdata+c3*p->fontheight;
cdat4 = p->fontdata+c4*p->fontheight;
for (rows = p->fontheight; rows--;) {
+#if defined(__BIG_ENDIAN)
d = *cdat1++<<24 | *cdat2++<<16 | *cdat3++<<8 | *cdat4++;
+#elif defined(__LITTLE_ENDIAN)
+ d = *cdat1++ | *cdat2++<<8 | *cdat3++<<16 | *cdat4++<<32);
+#else
+#error FIXME: No endianness??
+#endif
fg = fg0;
bg = bg0;
for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
- if (bg & 1)
+ if (bg & 1){
if (fg & 1)
- *(u_long *)dest = 0xffffffff;
+ *(u32 *)dest = 0xffffffff;
else
- *(u_long *)dest = ~d;
- else
+ *(u32 *)dest = ~d;
+ }else{
if (fg & 1)
- *(u_long *)dest = d;
+ *(u32 *)dest = d;
else
- *(u_long *)dest = 0x00000000;
+ *(u32 *)dest = 0x00000000;
+ }
bg >>= 1;
fg >>= 1;
}
@@ -257,9 +230,9 @@ static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
}
}
-static void rev_char_ilbm(struct display *p, int xx, int yy)
+void fbcon_ilbm_revc(struct display *p, int xx, int yy)
{
- u_char *dest, *dest0;
+ u8 *dest, *dest0;
u_int rows, i;
int mask;
@@ -283,18 +256,24 @@ static void rev_char_ilbm(struct display *p, int xx, int yy)
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_ilbm(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_ilbm, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_ilbm);
-}
-#endif /* MODULE */
+struct display_switch fbcon_ilbm = {
+ fbcon_ilbm_setup, fbcon_ilbm_bmove, fbcon_ilbm_clear, fbcon_ilbm_putc,
+ fbcon_ilbm_putcs, fbcon_ilbm_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_ilbm);
+EXPORT_SYMBOL(fbcon_ilbm_setup);
+EXPORT_SYMBOL(fbcon_ilbm_bmove);
+EXPORT_SYMBOL(fbcon_ilbm_clear);
+EXPORT_SYMBOL(fbcon_ilbm_putc);
+EXPORT_SYMBOL(fbcon_ilbm_putcs);
+EXPORT_SYMBOL(fbcon_ilbm_revc);
diff --git a/drivers/video/fbcon-ilbm.h b/drivers/video/fbcon-ilbm.h
new file mode 100644
index 000000000..e2434c7d1
--- /dev/null
+++ b/drivers/video/fbcon-ilbm.h
@@ -0,0 +1,15 @@
+ /*
+ * Amiga interleaved bitplanes (ilbm)
+ */
+
+extern struct display_switch fbcon_ilbm;
+extern void fbcon_ilbm_setup(struct display *p);
+extern void fbcon_ilbm_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_ilbm_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_ilbm_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_ilbm_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_ilbm_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-iplan2p2.c b/drivers/video/fbcon-iplan2p2.c
index 3973a0013..adef5819d 100644
--- a/drivers/video/fbcon-iplan2p2.c
+++ b/drivers/video/fbcon-iplan2p2.c
@@ -14,41 +14,13 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
-#include "fbcon.h"
-
-
-#ifndef __mc68000__
-#error No support for non-m68k yet
-#endif
+#include <asm/byteorder.h>
-
- /*
- * Prototypes
- */
-
-static int open_iplan2p2(struct display *p);
-static void release_iplan2p2(void);
-static void bmove_iplan2p2(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_iplan2p2(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width);
-static void putc_iplan2p2(struct vc_data *conp, struct display *p, int c,
- int yy, int xx);
-static void putcs_iplan2p2(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx);
-static void rev_char_iplan2p2(struct display *display, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_iplan2p2 = {
- open_iplan2p2, release_iplan2p2, bmove_iplan2p2, clear_iplan2p2,
- putc_iplan2p2, putcs_iplan2p2, rev_char_iplan2p2
-};
+#include "fbcon.h"
+#include "fbcon-iplan2p2.h"
/*
@@ -65,8 +37,19 @@ static struct display_switch dispsw_iplan2p2 = {
* The intensity bit (b3) is shifted into b1.
*/
-#define COLOR_2P(c) (((c & 7) >= 3 && (c & 7) != 4) | (c & 8) >> 2)
+static const u8 color_2p[] = { 0, 0, 0, 1, 0, 1, 1, 1, 2, 2, 2, 3, 2, 3, 3, 3 };
+#define COLOR_2P(c) color_2p[c]
+/* Perform the m68k movepw operation. */
+static inline void movepw(u8 *d, u16 val)
+{
+#if defined __mc68000__ && !defined CONFIG_OPTIMIZE_060
+ asm volatile ("movepw %1,%0@(0)" : : "a" (d), "d" (val));
+#else
+ d[0] = (val >> 16) & 0xff;
+ d[2] = val & 0xff;
+#endif
+}
/* Sets the bytes in the visible column at d, height h, to the value
* val for a 2 plane screen. The the bis of the color in 'color' are
@@ -77,16 +60,13 @@ static struct display_switch dispsw_iplan2p2 = {
* *(d+2) = (color & 2) ? 0xff : 0;
*/
-static __inline__ void memclear_2p_col(void *d, size_t h, u_short val, int bpr)
+static __inline__ void memclear_2p_col(void *d, size_t h, u16 val, int bpr)
{
-#ifdef __mc68000__
- __asm__ __volatile__ ("1: movepw %4,%0@(0)\n\t"
- "addal %5,%0\n\t"
- "dbra %1,1b"
- : "=a" (d), "=d" (h)
- : "0" (d), "1" (h - 1), "d" (val), "r" (bpr));
-#else /* !m68k */
-#endif /* !m68k */
+ u8 *dd = d;
+ do {
+ movepw(dd, val);
+ dd += bpr;
+ } while (--h);
}
/* Sets a 2 plane region from 'd', length 'count' bytes, to the color
@@ -98,9 +78,9 @@ static __inline__ void memclear_2p_col(void *d, size_t h, u_short val, int bpr)
* *(d+2) = *(d+3) = (color & 2) ? 0xff : 0;
*/
-static __inline__ void memset_even_2p(void *d, size_t count, u_long val)
+static __inline__ void memset_even_2p(void *d, size_t count, u32 val)
{
- u_long *dd = d;
+ u32 *dd = d;
count /= 4;
while (count--)
@@ -111,7 +91,7 @@ static __inline__ void memset_even_2p(void *d, size_t count, u_long val)
static __inline__ void memmove_2p_col (void *d, void *s, int h, int bpr)
{
- u_char *dd = d, *ss = s;
+ u8 *dd = d, *ss = s;
while (h--) {
dd[0] = ss[0];
@@ -124,81 +104,54 @@ static __inline__ void memmove_2p_col (void *d, void *s, int h, int bpr)
/* This expands a 2 bit color into a short for movepw (2 plane) operations. */
-static __inline__ u_short expand2w(u_char c)
+static const u16 two2byte[] = {
+ 0x0000, 0xff00, 0x00ff, 0xffff
+};
+
+static __inline__ u16 expand2w(u8 c)
{
- u_short rv;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("lsrb #1,%2\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%2\n\t"
- "scs %0\n\t"
- : "=&d" (rv), "=d" (c)
- : "1" (c));
-#endif /* !m68k */
- return(rv);
+ return two2byte[c];
}
+
/* This expands a 2 bit color into one long for a movel operation
* (2 planes).
*/
-static __inline__ u_long expand2l(u_char c)
+static const u32 two2word[] = {
+#ifndef __LITTLE_ENDIAN
+ 0x00000000, 0xffff0000, 0x0000ffff, 0xffffffff
+#else
+ 0x00000000, 0x0000ffff, 0xffff0000, 0xffffffff
+#endif
+};
+
+static __inline__ u32 expand2l(u8 c)
{
- u_long rv;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("lsrb #1,%2\n\t"
- "scs %0\n\t"
- "extw %0\n\t"
- "swap %0\n\t"
- "lsrb #1,%2\n\t"
- "scs %0\n\t"
- "extw %0\n\t"
- : "=&d" (rv), "=d" (c)
- : "1" (c));
-#endif /* !m68k */
- return rv;
+ return two2word[c];
}
/* This duplicates a byte 2 times into a short. */
-static __inline__ u_short dup2w(u_char c)
+static __inline__ u16 dup2w(u8 c)
{
- ushort rv;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("moveb %1,%0\n\t"
- "lslw #8,%0\n\t"
- "moveb %1,%0\n\t"
- : "=&d" (rv)
- : "d" (c));
-#endif /* !m68k */
- return( rv );
+ u16 rv;
+
+ rv = c;
+ rv |= c << 8;
+ return rv;
}
-static int open_iplan2p2(struct display *p)
+void fbcon_iplan2p2_setup(struct display *p)
{
- if (p->type != FB_TYPE_INTERLEAVED_PLANES || p->type_aux != 2 ||
- p->var.bits_per_pixel != 2)
- return -EINVAL;
-
p->next_line = p->var.xres_virtual>>2;
p->next_plane = 2;
- MOD_INC_USE_COUNT;
- return 0;
}
-static void release_iplan2p2(void)
-{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_iplan2p2(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
+void fbcon_iplan2p2_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
/* bmove() has to distinguish two major cases: If both, source and
* destination, start at even addresses or both are at odd
@@ -212,7 +165,7 @@ static void bmove_iplan2p2(struct display *p, int sy, int sx, int dy, int dx,
* all movements by memmove_col().
*/
- if (sx == 0 && dx == 0 && width == p->next_line/2) {
+ if (sx == 0 && dx == 0 && width * 2 == p->next_line) {
/* Special (but often used) case: Moving whole lines can be
* done with memmove()
*/
@@ -221,8 +174,8 @@ static void bmove_iplan2p2(struct display *p, int sy, int sx, int dy, int dx,
p->next_line * height * p->fontheight);
} else {
int rows, cols;
- u_char *src;
- u_char *dst;
+ u8 *src;
+ u8 *dst;
int bytes = p->next_line;
int linesize = bytes * p->fontheight;
u_int colsize = height * p->fontheight;
@@ -298,21 +251,21 @@ static void bmove_iplan2p2(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_iplan2p2(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width)
+void fbcon_iplan2p2_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
{
- ulong offset;
- u_char *start;
+ u32 offset;
+ u8 *start;
int rows;
int bytes = p->next_line;
int lines = height * p->fontheight;
- ulong size;
- u_long cval;
- u_short pcval;
+ u32 size;
+ u32 cval;
+ u16 pcval;
cval = expand2l (COLOR_2P (attr_bgcol_ec(p,conp)));
- if (sx == 0 && width == bytes/2) {
+ if (sx == 0 && width * 2 == bytes) {
offset = sy * bytes * p->fontheight;
size = lines * bytes;
memset_even_2p(p->screen_base+offset, size, cval);
@@ -344,14 +297,14 @@ static void clear_iplan2p2(struct vc_data *conp, struct display *p, int sy,
}
}
-static void putc_iplan2p2(struct vc_data *conp, struct display *p, int c,
- int yy, int xx)
+void fbcon_iplan2p2_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx)
{
- u_char *dest;
- u_char *cdat;
+ u8 *dest;
+ u8 *cdat;
int rows;
int bytes = p->next_line;
- ulong eorx, fgx, bgx, fdx;
+ u16 eorx, fgx, bgx, fdx;
c &= 0xff;
@@ -364,22 +317,18 @@ static void putc_iplan2p2(struct vc_data *conp, struct display *p, int c,
for (rows = p->fontheight ; rows-- ; dest += bytes) {
fdx = dup2w(*cdat++);
-#ifdef __mc68000__
- __asm__ __volatile__ ("movepw %1,%0@(0)"
- : /* no outputs */
- : "a" (dest), "d" ((fdx & eorx) ^ bgx));
-#endif /* !m68k */
+ movepw(dest, (fdx & eorx) ^ bgx);
}
}
-static void putcs_iplan2p2(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx)
+void fbcon_iplan2p2_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx)
{
- u_char *dest, *dest0;
- u_char *cdat, c;
+ u8 *dest, *dest0;
+ u8 *cdat, c;
int rows;
int bytes;
- ulong eorx, fgx, bgx, fdx;
+ u16 eorx, fgx, bgx, fdx;
bytes = p->next_line;
dest0 = p->screen_base + yy * p->fontheight * bytes + (xx>>1)*4 + (xx & 1);
@@ -393,19 +342,15 @@ static void putcs_iplan2p2(struct vc_data *conp, struct display *p,
for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
fdx = dup2w(*cdat++);
-#ifdef __mc68000__
- __asm__ __volatile__ ("movepw %1,%0@(0)"
- : /* no outputs */
- : "a" (dest), "d" ((fdx & eorx) ^ bgx));
-#endif /* !m68k */
+ movepw(dest, (fdx & eorx) ^ bgx);
}
INC_2P(dest0);
}
}
-static void rev_char_iplan2p2(struct display *p, int xx, int yy)
+void fbcon_iplan2p2_revc(struct display *p, int xx, int yy)
{
- u_char *dest;
+ u8 *dest;
int j;
int bytes;
@@ -425,18 +370,24 @@ static void rev_char_iplan2p2(struct display *p, int xx, int yy)
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_iplan2p2(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_iplan2p2, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_iplan2p2);
-}
-#endif /* MODULE */
+struct display_switch fbcon_iplan2p2 = {
+ fbcon_iplan2p2_setup, fbcon_iplan2p2_bmove, fbcon_iplan2p2_clear,
+ fbcon_iplan2p2_putc, fbcon_iplan2p2_putcs, fbcon_iplan2p2_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_iplan2p2);
+EXPORT_SYMBOL(fbcon_iplan2p2_setup);
+EXPORT_SYMBOL(fbcon_iplan2p2_bmove);
+EXPORT_SYMBOL(fbcon_iplan2p2_clear);
+EXPORT_SYMBOL(fbcon_iplan2p2_putc);
+EXPORT_SYMBOL(fbcon_iplan2p2_putcs);
+EXPORT_SYMBOL(fbcon_iplan2p2_revc);
diff --git a/drivers/video/fbcon-iplan2p2.h b/drivers/video/fbcon-iplan2p2.h
new file mode 100644
index 000000000..ae18a1b32
--- /dev/null
+++ b/drivers/video/fbcon-iplan2p2.h
@@ -0,0 +1,15 @@
+ /*
+ * Atari interleaved bitplanes (2 planes) (iplan2p2)
+ */
+
+extern struct display_switch fbcon_iplan2p2;
+extern void fbcon_iplan2p2_setup(struct display *p);
+extern void fbcon_iplan2p2_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width);
+extern void fbcon_iplan2p2_clear(struct vc_data *conp, struct display *p,
+ int sy, int sx, int height, int width);
+extern void fbcon_iplan2p2_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_iplan2p2_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_iplan2p2_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-iplan2p4.c b/drivers/video/fbcon-iplan2p4.c
index e3a10f0ea..b299701c4 100644
--- a/drivers/video/fbcon-iplan2p4.c
+++ b/drivers/video/fbcon-iplan2p4.c
@@ -14,41 +14,13 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
-#include "fbcon.h"
-
-
-#ifndef __mc68000__
-#error No support for non-m68k yet
-#endif
-
-
- /*
- * Prototypes
- */
-
-static int open_iplan2p4(struct display *p);
-static void release_iplan2p4(void);
-static void bmove_iplan2p4(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_iplan2p4(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width);
-static void putc_iplan2p4(struct vc_data *conp, struct display *p, int c,
- int yy, int xx);
-static void putcs_iplan2p4(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx);
-static void rev_char_iplan2p4(struct display *p, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
+#include <asm/byteorder.h>
-static struct display_switch dispsw_iplan2p4 = {
- open_iplan2p4, release_iplan2p4, bmove_iplan2p4, clear_iplan2p4,
- putc_iplan2p4, putcs_iplan2p4, rev_char_iplan2p4
-};
+#include "fbcon.h"
+#include "fbcon-iplan2p4.h"
/*
@@ -60,6 +32,18 @@ static struct display_switch dispsw_iplan2p4 = {
#define INC_4P(p) do { if (!((long)(++(p)) & 1)) (p) += 6; } while(0)
#define DEC_4P(p) do { if ((long)(--(p)) & 1) (p) -= 6; } while(0)
+/* Perform the m68k movepl operation. */
+static inline void movepl(u8 *d, u32 val)
+{
+#if defined __mc68000__ && !defined CONFIG_OPTIMIZE_060
+ asm volatile ("movepl %1,%0@(0)" : : "a" (d), "d" (val));
+#else
+ d[0] = (val >> 24) & 0xff;
+ d[2] = (val >> 16) & 0xff;
+ d[4] = (val >> 8) & 0xff;
+ d[6] = val & 0xff;
+#endif
+}
/* Sets the bytes in the visible column at d, height h, to the value
* val for a 4 plane screen. The the bis of the color in 'color' are
@@ -72,15 +56,13 @@ static struct display_switch dispsw_iplan2p4 = {
* *(d+6) = (color & 8) ? 0xff : 0;
*/
-static __inline__ void memclear_4p_col(void *d, size_t h, u_long val, int bpr)
+static __inline__ void memclear_4p_col(void *d, size_t h, u32 val, int bpr)
{
-#ifdef __mc68000__
- __asm__ __volatile__ ("1: movepl %4,%0@(0)\n\t"
- "addal %5,%0\n\t"
- "dbra %1,1b"
- : "=a" (d), "=d" (h)
- : "0" (d), "1" (h - 1), "d" (val), "r" (bpr));
-#endif /* !m68k */
+ u8 *dd = d;
+ do {
+ movepl(dd, val);
+ dd += bpr;
+ } while (--h);
}
/* Sets a 4 plane region from 'd', length 'count' bytes, to the color
@@ -94,10 +76,10 @@ static __inline__ void memclear_4p_col(void *d, size_t h, u_long val, int bpr)
* *(d+6) = *(d+7) = (color & 8) ? 0xff : 0;
*/
-static __inline__ void memset_even_4p(void *d, size_t count, u_long val1,
- u_long val2)
+static __inline__ void memset_even_4p(void *d, size_t count, u32 val1,
+ u32 val2)
{
- u_long *dd = d;
+ u32 *dd = d;
count /= 8;
while (count--) {
@@ -110,7 +92,7 @@ static __inline__ void memset_even_4p(void *d, size_t count, u_long val1,
static __inline__ void memmove_4p_col (void *d, void *s, int h, int bpr)
{
- u_char *dd = d, *ss = s;
+ u8 *dd = d, *ss = s;
while (h--) {
dd[0] = ss[0];
@@ -125,99 +107,59 @@ static __inline__ void memmove_4p_col (void *d, void *s, int h, int bpr)
/* This expands a 4 bit color into a long for movepl (4 plane) operations. */
-static __inline__ u_long expand4l(u_char c)
+static const u32 four2byte[] = {
+ 0x00000000, 0xff000000, 0x00ff0000, 0xffff0000,
+ 0x0000ff00, 0xff00ff00, 0x00ffff00, 0xffffff00,
+ 0x000000ff, 0xff0000ff, 0x00ff00ff, 0xffff00ff,
+ 0x0000ffff, 0xff00ffff, 0x00ffffff, 0xffffffff
+};
+
+static __inline__ u32 expand4l(u8 c)
{
- u_long rv;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("lsrb #1,%2\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%2\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%2\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%2\n\t"
- "scs %0\n\t"
- : "=&d" (rv), "=d" (c)
- : "1" (c));
-#endif /* !m68k */
- return(rv);
+ return four2byte[c];
}
+
/* This expands a 4 bit color into two longs for two movel operations
* (4 planes).
*/
-static __inline__ void expand4dl(u_char c, u_long *ret1, u_long *ret2)
+static const u32 two2word[] = {
+#ifndef __LITTLE_ENDIAN
+ 0x00000000, 0xffff0000, 0x0000ffff, 0xffffffff,
+#else
+ 0x00000000, 0x0000ffff, 0xffff0000, 0xffffffff,
+#endif
+};
+
+static __inline__ void expand4dl(u8 c, u32 *ret1, u32 *ret2)
{
- u_long rv1, rv2;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("lsrb #1,%3\n\t"
- "scs %0\n\t"
- "extw %0\n\t"
- "swap %0\n\t"
- "lsrb #1,%3\n\t"
- "scs %0\n\t"
- "extw %0\n\t"
- "lsrb #1,%3\n\t"
- "scs %1\n\t"
- "extw %1\n\t"
- "swap %1\n\t"
- "lsrb #1,%3\n\t"
- "scs %1\n\t"
- "extw %1"
- : "=&d" (rv1), "=&d" (rv2), "=d" (c)
- : "2" (c));
-#endif /* !m68k */
- *ret1 = rv1;
- *ret2 = rv2;
+ *ret1 = two2word[c & 3];
+ *ret2 = two2word[c >> 2];
}
/* This duplicates a byte 4 times into a long. */
-static __inline__ u_long dup4l(u_char c)
+static __inline__ u32 dup4l(u8 c)
{
- ushort tmp;
- ulong rv;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("moveb %2,%0\n\t"
- "lslw #8,%0\n\t"
- "moveb %2,%0\n\t"
- "movew %0,%1\n\t"
- "swap %0\n\t"
- "movew %1,%0"
- : "=&d" (rv), "=d" (tmp)
- : "d" (c));
-#endif /* !m68k */
- return(rv);
+ u32 rv;
+
+ rv = c;
+ rv |= rv << 8;
+ rv |= rv << 16;
+ return rv;
}
-static int open_iplan2p4(struct display *p)
+void fbcon_iplan2p4_setup(struct display *p)
{
- if (p->type != FB_TYPE_INTERLEAVED_PLANES || p->type_aux != 2 ||
- p->var.bits_per_pixel != 4)
- return -EINVAL;
-
p->next_line = p->var.xres_virtual>>1;
p->next_plane = 2;
- MOD_INC_USE_COUNT;
- return 0;
}
-static void release_iplan2p4(void)
-{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_iplan2p4(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
+void fbcon_iplan2p4_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
/* bmove() has to distinguish two major cases: If both, source and
* destination, start at even addresses or both are at odd
@@ -231,7 +173,7 @@ static void bmove_iplan2p4(struct display *p, int sy, int sx, int dy, int dx,
* all movements by memmove_col().
*/
- if (sx == 0 && dx == 0 && width == p->next_line/4) {
+ if (sx == 0 && dx == 0 && width * 4 == p->next_line) {
/* Special (but often used) case: Moving whole lines can be
*done with memmove()
*/
@@ -240,8 +182,8 @@ static void bmove_iplan2p4(struct display *p, int sy, int sx, int dy, int dx,
p->next_line * height * p->fontheight);
} else {
int rows, cols;
- u_char *src;
- u_char *dst;
+ u8 *src;
+ u8 *dst;
int bytes = p->next_line;
int linesize = bytes * p->fontheight;
u_int colsize = height * p->fontheight;
@@ -320,20 +262,20 @@ static void bmove_iplan2p4(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_iplan2p4(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width)
+void fbcon_iplan2p4_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
{
- ulong offset;
- u_char *start;
+ u32 offset;
+ u8 *start;
int rows;
int bytes = p->next_line;
int lines = height * p->fontheight;
- ulong size;
- u_long cval1, cval2, pcval;
+ u32 size;
+ u32 cval1, cval2, pcval;
expand4dl(attr_bgcol_ec(p,conp), &cval1, &cval2);
- if (sx == 0 && width == bytes/4) {
+ if (sx == 0 && width * 4 == bytes) {
offset = sy * bytes * p->fontheight;
size = lines * bytes;
memset_even_4p(p->screen_base+offset, size, cval1, cval2);
@@ -365,14 +307,14 @@ static void clear_iplan2p4(struct vc_data *conp, struct display *p, int sy,
}
}
-static void putc_iplan2p4(struct vc_data *conp, struct display *p, int c,
- int yy, int xx)
+void fbcon_iplan2p4_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx)
{
- u_char *dest;
- u_char *cdat;
+ u8 *dest;
+ u8 *cdat;
int rows;
int bytes = p->next_line;
- ulong eorx, fgx, bgx, fdx;
+ u32 eorx, fgx, bgx, fdx;
c &= 0xff;
@@ -385,22 +327,18 @@ static void putc_iplan2p4(struct vc_data *conp, struct display *p, int c,
for(rows = p->fontheight ; rows-- ; dest += bytes) {
fdx = dup4l(*cdat++);
-#ifdef __mc68000__
- __asm__ __volatile__ ("movepl %1,%0@(0)"
- : /* no outputs */
- : "a" (dest), "d" ((fdx & eorx) ^ bgx));
-#endif /* !m68k */
+ movepl(dest, (fdx & eorx) ^ bgx);
}
}
-static void putcs_iplan2p4(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx)
+void fbcon_iplan2p4_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx)
{
- u_char *dest, *dest0;
- u_char *cdat, c;
+ u8 *dest, *dest0;
+ u8 *cdat, c;
int rows;
int bytes;
- ulong eorx, fgx, bgx, fdx;
+ u32 eorx, fgx, bgx, fdx;
bytes = p->next_line;
dest0 = p->screen_base + yy * p->fontheight * bytes + (xx>>1)*8 + (xx & 1);
@@ -421,19 +359,15 @@ static void putcs_iplan2p4(struct vc_data *conp, struct display *p,
for(rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
fdx = dup4l(*cdat++);
-#ifdef __mc68000__
- __asm__ __volatile__ ("movepl %1,%0@(0)"
- : /* no outputs */
- : "a" (dest), "d" ((fdx & eorx) ^ bgx));
-#endif /* !m68k */
+ movepl(dest, (fdx & eorx) ^ bgx);
}
INC_4P(dest0);
}
}
-static void rev_char_iplan2p4(struct display *p, int xx, int yy)
+void fbcon_iplan2p4_revc(struct display *p, int xx, int yy)
{
- u_char *dest;
+ u8 *dest;
int j;
int bytes;
@@ -456,18 +390,24 @@ static void rev_char_iplan2p4(struct display *p, int xx, int yy)
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_iplan2p4(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_iplan2p4, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_iplan2p4);
-}
-#endif /* MODULE */
+struct display_switch fbcon_iplan2p4 = {
+ fbcon_iplan2p4_setup, fbcon_iplan2p4_bmove, fbcon_iplan2p4_clear,
+ fbcon_iplan2p4_putc, fbcon_iplan2p4_putcs, fbcon_iplan2p4_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_iplan2p4);
+EXPORT_SYMBOL(fbcon_iplan2p4_setup);
+EXPORT_SYMBOL(fbcon_iplan2p4_bmove);
+EXPORT_SYMBOL(fbcon_iplan2p4_clear);
+EXPORT_SYMBOL(fbcon_iplan2p4_putc);
+EXPORT_SYMBOL(fbcon_iplan2p4_putcs);
+EXPORT_SYMBOL(fbcon_iplan2p4_revc);
diff --git a/drivers/video/fbcon-iplan2p4.h b/drivers/video/fbcon-iplan2p4.h
new file mode 100644
index 000000000..ae3b38494
--- /dev/null
+++ b/drivers/video/fbcon-iplan2p4.h
@@ -0,0 +1,15 @@
+ /*
+ * Atari interleaved bitplanes (4 planes) (iplan2p4)
+ */
+
+extern struct display_switch fbcon_iplan2p4;
+extern void fbcon_iplan2p4_setup(struct display *p);
+extern void fbcon_iplan2p4_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width);
+extern void fbcon_iplan2p4_clear(struct vc_data *conp, struct display *p,
+ int sy, int sx, int height, int width);
+extern void fbcon_iplan2p4_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_iplan2p4_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_iplan2p4_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-iplan2p8.c b/drivers/video/fbcon-iplan2p8.c
index 78f2f2e0e..5ea15c26b 100644
--- a/drivers/video/fbcon-iplan2p8.c
+++ b/drivers/video/fbcon-iplan2p8.c
@@ -14,41 +14,13 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
-#include "fbcon.h"
-
-
-#ifndef __mc68000__
-#error No support for non-m68k yet
-#endif
-
-
- /*
- * Prototypes
- */
-
-static int open_iplan2p8(struct display *p);
-static void release_iplan2p8(void);
-static void bmove_iplan2p8(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_iplan2p8(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width);
-static void putc_iplan2p8(struct vc_data *conp, struct display *p, int c,
- int yy, int xx);
-static void putcs_iplan2p8(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx);
-static void rev_char_iplan2p8(struct display *display, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
+#include <asm/byteorder.h>
-static struct display_switch dispsw_iplan2p8 = {
- open_iplan2p8, release_iplan2p8, bmove_iplan2p8, clear_iplan2p8,
- putc_iplan2p8, putcs_iplan2p8, rev_char_iplan2p8
-};
+#include "fbcon.h"
+#include "fbcon-iplan2p8.h"
/*
@@ -65,9 +37,26 @@ static struct display_switch dispsw_iplan2p8 = {
#define INC_8P(p) do { if (!((long)(++(p)) & 1)) (p) += 14; } while(0)
#define DEC_8P(p) do { if ((long)(--(p)) & 1) (p) -= 14; } while(0)
+/* Perform the m68k movepl operation extended to 64 bits. */
+static inline void movepl2(u8 *d, u32 val1, u32 val2)
+{
+#if defined __mc68000__ && !defined CONFIG_OPTIMIZE_060
+ asm volatile ("movepl %1,%0@(0); movepl %2,%0@(8)"
+ : : "a" (d), "d" (val1), "d" (val2));
+#else
+ d[0] = (val1 >> 24) & 0xff;
+ d[2] = (val1 >> 16) & 0xff;
+ d[4] = (val1 >> 8) & 0xff;
+ d[6] = val1 & 0xff;
+ d[8] = (val2 >> 24) & 0xff;
+ d[10] = (val2 >> 16) & 0xff;
+ d[12] = (val2 >> 8) & 0xff;
+ d[14] = val2 & 0xff;
+#endif
+}
/* Sets the bytes in the visible column at d, height h, to the value
- * val1,val2 for a 8 plane screen. The the bis of the color in 'color' are
+ * val1,val2 for a 8 plane screen. The bits of the color in 'color' are
* moved (8 times) to the respective bytes. This means:
*
* for(h times; d += bpr)
@@ -81,18 +70,14 @@ static struct display_switch dispsw_iplan2p8 = {
* *(d+14) = (color & 128) ? 0xff : 0;
*/
-static __inline__ void memclear_8p_col(void *d, size_t h, u_long val1,
- u_long val2, int bpr)
+static __inline__ void memclear_8p_col(void *d, size_t h, u32 val1,
+ u32 val2, int bpr)
{
-#ifdef __mc68000__
- __asm__ __volatile__ ("1: movepl %4,%0@(0)\n\t"
- "movepl %5,%0@(8)\n\t"
- "addal %6,%0\n\t"
- "dbra %1,1b"
- : "=a" (d), "=d" (h)
- : "0" (d), "1" (h - 1), "d" (val1), "d" (val2),
- "r" (bpr));
-#endif /* !m68k */
+ u8 *dd = d;
+ do {
+ movepl2(dd, val1, val2);
+ dd += bpr;
+ } while (--h);
}
/* Sets a 8 plane region from 'd', length 'count' bytes, to the color
@@ -110,10 +95,10 @@ static __inline__ void memclear_8p_col(void *d, size_t h, u_long val1,
* *(d+14) = *(d+15) = (color & 128) ? 0xff : 0;
*/
-static __inline__ void memset_even_8p(void *d, size_t count, u_long val1,
- u_long val2, u_long val3, u_long val4)
+static __inline__ void memset_even_8p(void *d, size_t count, u32 val1,
+ u32 val2, u32 val3, u32 val4)
{
- u_long *dd = d;
+ u32 *dd = d;
count /= 16;
while (count--) {
@@ -128,7 +113,7 @@ static __inline__ void memset_even_8p(void *d, size_t count, u_long val1,
static __inline__ void memmove_8p_col (void *d, void *s, int h, int bpr)
{
- u_char *dd = d, *ss = s;
+ u8 *dd = d, *ss = s;
while (h--) {
dd[0] = ss[0];
@@ -149,124 +134,64 @@ static __inline__ void memmove_8p_col (void *d, void *s, int h, int bpr)
* operations.
*/
-static __inline__ void expand8dl(u_char c, u_long *ret1, u_long *ret2)
+static const u32 four2long[] =
+{
+ 0x00000000, 0xff000000, 0x00ff0000, 0xffff0000,
+ 0x0000ff00, 0xff00ff00, 0x00ffff00, 0xffffff00,
+ 0x000000ff, 0xff0000ff, 0x00ff00ff, 0xffff00ff,
+ 0x0000ffff, 0xff00ffff, 0x00ffffff, 0xffffffff,
+};
+
+static __inline__ void expand8dl(u8 c, u32 *ret1, u32 *ret2)
{
- u_long rv1, rv2;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("lsrb #1,%3\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%3\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%3\n\t"
- "scs %0\n\t"
- "lsll #8,%0\n\t"
- "lsrb #1,%3\n\t"
- "scs %0\n\t"
- "lsrb #1,%3\n\t"
- "scs %1\n\t"
- "lsll #8,%1\n\t"
- "lsrb #1,%3\n\t"
- "scs %1\n\t"
- "lsll #8,%1\n\t"
- "lsrb #1,%3\n\t"
- "scs %1\n\t"
- "lsll #8,%1\n\t"
- "lsrb #1,%3\n\t"
- "scs %1"
- : "=&d" (rv1), "=&d" (rv2),"=d" (c)
- : "2" (c));
-#endif /* !m68k */
- *ret1 = rv1;
- *ret2 = rv2;
+ *ret1 = four2long[c & 15];
+ *ret2 = four2long[c >> 4];
}
+
/* This expands a 8 bit color into four longs for four movel operations
* (8 planes).
*/
-#ifdef __mc68000__
-/* ++andreas: use macro to avoid taking address of return values */
-#define expand8ql(c, rv1, rv2, rv3, rv4) \
- do { \
- u_char tmp = c; \
- __asm__ __volatile__ ("lsrb #1,%5\n\t" \
- "scs %0\n\t" \
- "extw %0\n\t" \
- "swap %0\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %0\n\t" \
- "extw %0\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %1\n\t" \
- "extw %1\n\t" \
- "swap %1\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %1\n\t" \
- "extw %1\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %2\n\t" \
- "extw %2\n\t" \
- "swap %2\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %2\n\t" \
- "extw %2\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %3\n\t" \
- "extw %3\n\t" \
- "swap %3\n\t" \
- "lsrb #1,%5\n\t" \
- "scs %3\n\t" \
- "extw %3" \
- : "=&d" (rv1), "=&d" (rv2), "=&d" (rv3), \
- "=&d" (rv4), "=d" (tmp) \
- : "4" (tmp)); \
- } while (0)
-#endif /* !m68k */
+static const u32 two2word[] =
+{
+#ifndef __LITTLE_ENDIAN
+ 0x00000000, 0xffff0000, 0x0000ffff, 0xffffffff
+#else
+ 0x00000000, 0x0000ffff, 0xffff0000, 0xffffffff
+#endif
+};
+
+static inline void expand8ql(u8 c, u32 *rv1, u32 *rv2, u32 *rv3, u32 *rv4)
+{
+ *rv1 = two2word[c & 4];
+ *rv2 = two2word[(c >> 2) & 4];
+ *rv3 = two2word[(c >> 4) & 4];
+ *rv4 = two2word[c >> 6];
+}
/* This duplicates a byte 4 times into a long. */
-static __inline__ u_long dup4l(u_char c)
+static __inline__ u32 dup4l(u8 c)
{
- ushort tmp;
- ulong rv;
-
-#ifdef __mc68000__
- __asm__ __volatile__ ("moveb %2,%0\n\t"
- "lslw #8,%0\n\t"
- "moveb %2,%0\n\t"
- "movew %0,%1\n\t"
- "swap %0\n\t"
- "movew %1,%0"
- : "=&d" (rv), "=d" (tmp)
- : "d" (c));
-#endif /* !m68k */
- return(rv);
+ u32 rv;
+
+ rv = c;
+ rv |= rv << 8;
+ rv |= rv << 16;
+ return rv;
}
-static int open_iplan2p8(struct display *p)
+void fbcon_iplan2p8_setup(struct display *p)
{
- if (p->type != FB_TYPE_INTERLEAVED_PLANES || p->type_aux != 2 ||
- p->var.bits_per_pixel != 8)
- return -EINVAL;
-
p->next_line = p->var.xres_virtual;
p->next_plane = 2;
- MOD_INC_USE_COUNT;
- return 0;
-}
-
-static void release_iplan2p8(void)
-{
- MOD_DEC_USE_COUNT;
}
-static void bmove_iplan2p8(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
+void fbcon_iplan2p8_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
/* bmove() has to distinguish two major cases: If both, source and
* destination, start at even addresses or both are at odd
@@ -280,7 +205,7 @@ static void bmove_iplan2p8(struct display *p, int sy, int sx, int dy, int dx,
* all movements by memmove_col().
*/
- if (sx == 0 && dx == 0 && width == p->next_line/8) {
+ if (sx == 0 && dx == 0 && width * 8 == p->next_line) {
/* Special (but often used) case: Moving whole lines can be
* done with memmove()
*/
@@ -289,8 +214,8 @@ static void bmove_iplan2p8(struct display *p, int sy, int sx, int dy, int dx,
p->next_line * height * p->fontheight);
} else {
int rows, cols;
- u_char *src;
- u_char *dst;
+ u8 *src;
+ u8 *dst;
int bytes = p->next_line;
int linesize = bytes * p->fontheight;
u_int colsize = height * p->fontheight;
@@ -369,20 +294,20 @@ static void bmove_iplan2p8(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_iplan2p8(struct vc_data *conp, struct display *p, int sy,
- int sx, int height, int width)
+void fbcon_iplan2p8_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
{
- ulong offset;
- u_char *start;
+ u32 offset;
+ u8 *start;
int rows;
int bytes = p->next_line;
int lines = height * p->fontheight;
- ulong size;
- u_long cval1, cval2, cval3, cval4, pcval1, pcval2;
+ u32 size;
+ u32 cval1, cval2, cval3, cval4, pcval1, pcval2;
- expand8ql(attr_bgcol_ec(p,conp), cval1, cval2, cval3, cval4);
+ expand8ql(attr_bgcol_ec(p,conp), &cval1, &cval2, &cval3, &cval4);
- if (sx == 0 && width == bytes/8) {
+ if (sx == 0 && width * 8 == bytes) {
offset = sy * bytes * p->fontheight;
size = lines * bytes;
memset_even_8p(p->screen_base+offset, size, cval1, cval2, cval3, cval4);
@@ -414,14 +339,14 @@ static void clear_iplan2p8(struct vc_data *conp, struct display *p, int sy,
}
}
-static void putc_iplan2p8(struct vc_data *conp, struct display *p, int c,
- int yy, int xx)
+void fbcon_iplan2p8_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx)
{
- u_char *dest;
- u_char *cdat;
+ u8 *dest;
+ u8 *cdat;
int rows;
int bytes = p->next_line;
- ulong eorx1, eorx2, fgx1, fgx2, bgx1, bgx2, fdx;
+ u32 eorx1, eorx2, fgx1, fgx2, bgx1, bgx2, fdx;
c &= 0xff;
@@ -434,24 +359,18 @@ static void putc_iplan2p8(struct vc_data *conp, struct display *p, int c,
for(rows = p->fontheight ; rows-- ; dest += bytes) {
fdx = dup4l(*cdat++);
-#ifdef __mc68000__
- __asm__ __volatile__ ("movepl %1,%0@(0)\n\t"
- "movepl %2,%0@(8)"
- : /* no outputs */
- : "a" (dest), "d" ((fdx & eorx1) ^ bgx1),
- "d" ((fdx & eorx2) ^ bgx2) );
-#endif /* !m68k */
+ movepl2(dest, (fdx & eorx1) ^ bgx1, (fdx & eorx2) ^ bgx2);
}
}
-static void putcs_iplan2p8(struct vc_data *conp, struct display *p,
- const char *s, int count, int yy, int xx)
+void fbcon_iplan2p8_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx)
{
- u_char *dest, *dest0;
- u_char *cdat, c;
+ u8 *dest, *dest0;
+ u8 *cdat, c;
int rows;
int bytes;
- ulong eorx1, eorx2, fgx1, fgx2, bgx1, bgx2, fdx;
+ u32 eorx1, eorx2, fgx1, fgx2, bgx1, bgx2, fdx;
bytes = p->next_line;
dest0 = p->screen_base + yy * p->fontheight * bytes + (xx>>1)*16 +
@@ -475,21 +394,15 @@ static void putcs_iplan2p8(struct vc_data *conp, struct display *p,
for(rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
fdx = dup4l(*cdat++);
-#ifdef __mc68000__
- __asm__ __volatile__ ("movepl %1,%0@(0)\n\t"
- "movepl %2,%0@(8)"
- : /* no outputs */
- : "a" (dest), "d" ((fdx & eorx1) ^ bgx1),
- "d" ((fdx & eorx2) ^ bgx2));
-#endif /* !m68k */
+ movepl2(dest, (fdx & eorx1) ^ bgx1, (fdx & eorx2) ^ bgx2);
}
INC_8P(dest0);
}
}
-static void rev_char_iplan2p8(struct display *p, int xx, int yy)
+void fbcon_iplan2p8_revc(struct display *p, int xx, int yy)
{
- u_char *dest;
+ u8 *dest;
int j;
int bytes;
@@ -502,7 +415,7 @@ static void rev_char_iplan2p8(struct display *p, int xx, int yy)
/* This should really obey the individual character's
* background and foreground colors instead of simply
* inverting. For 8 plane mode, only the lower 4 bits of the
- * color are inverted, because only that color registers have
+ * color are inverted, because only these color registers have
* been set up.
*/
dest[0] = ~dest[0];
@@ -514,18 +427,24 @@ static void rev_char_iplan2p8(struct display *p, int xx, int yy)
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_iplan2p8(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_iplan2p8, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_iplan2p8);
-}
-#endif /* MODULE */
+struct display_switch fbcon_iplan2p8 = {
+ fbcon_iplan2p8_setup, fbcon_iplan2p8_bmove, fbcon_iplan2p8_clear,
+ fbcon_iplan2p8_putc, fbcon_iplan2p8_putcs, fbcon_iplan2p8_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_iplan2p8);
+EXPORT_SYMBOL(fbcon_iplan2p8_setup);
+EXPORT_SYMBOL(fbcon_iplan2p8_bmove);
+EXPORT_SYMBOL(fbcon_iplan2p8_clear);
+EXPORT_SYMBOL(fbcon_iplan2p8_putc);
+EXPORT_SYMBOL(fbcon_iplan2p8_putcs);
+EXPORT_SYMBOL(fbcon_iplan2p8_revc);
diff --git a/drivers/video/fbcon-iplan2p8.h b/drivers/video/fbcon-iplan2p8.h
new file mode 100644
index 000000000..f2c46e229
--- /dev/null
+++ b/drivers/video/fbcon-iplan2p8.h
@@ -0,0 +1,15 @@
+ /*
+ * Atari interleaved bitplanes (8 planes) (iplan2p8)
+ */
+
+extern struct display_switch fbcon_iplan2p8;
+extern void fbcon_iplan2p8_setup(struct display *p);
+extern void fbcon_iplan2p8_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width);
+extern void fbcon_iplan2p8_clear(struct vc_data *conp, struct display *p,
+ int sy, int sx, int height, int width);
+extern void fbcon_iplan2p8_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_iplan2p8_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_iplan2p8_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-mac.c b/drivers/video/fbcon-mac.c
new file mode 100644
index 000000000..1dd5f1988
--- /dev/null
+++ b/drivers/video/fbcon-mac.c
@@ -0,0 +1,513 @@
+/*
+ * linux/drivers/video/fbcon-mac.c -- Low level frame buffer operations for
+ * x bpp packed pixels, font width != 8
+ *
+ * Created 26 Dec 1997 by Michael Schmitz
+ * Based on the old macfb.c 6x11 code by Randy Thelen
+ *
+ * This driver is significantly slower than the 8bit font drivers
+ * and would probably benefit from splitting into drivers for each depth.
+ *
+ * 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
+ */
+
+#include <linux/module.h>
+#include <linux/tty.h>
+#include <linux/console.h>
+#include <linux/string.h>
+#include <linux/config.h>
+#include <linux/fb.h>
+#include <linux/delay.h>
+
+#include "fbcon.h"
+#include "fbcon-mac.h"
+
+
+ /*
+ * variable bpp packed pixels
+ */
+
+static void plot_pixel_mac(struct display *p, int bw, int pixel_x,
+ int pixel_y);
+static int get_pixel_mac(struct display *p, int pixel_x, int pixel_y);
+
+void fbcon_mac_setup(struct display *p)
+{
+ if (p->line_length)
+ p->next_line = p->line_length;
+ else
+ p->next_line = p->var.xres_virtual>>3;
+ p->next_plane = 0;
+}
+
+
+ /*
+ * Macintosh
+ */
+#define PIXEL_BLACK_MAC 0
+#define PIXEL_WHITE_MAC 1
+#define PIXEL_INVERT_MAC 2
+
+void fbcon_mac_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ int i, j;
+ u8 *dest, *src;
+ int l,r,t,b,w,lo,s;
+ int dl,dr,dt,db,dw,dlo;
+ int move_up;
+
+ src = (u8 *) (p->screen_base + sy * p->fontheight * p->next_line);
+ dest = (u8 *) (p->screen_base + dy * p->fontheight * p->next_line);
+
+ if( sx == 0 && width == p->conp->vc_cols) {
+ s = height * p->fontheight * p->next_line;
+ mymemmove(dest, src, s);
+ return;
+ }
+
+ l = sx * p->fontwidth;
+ r = l + width * p->fontwidth;
+ t = sy * p->fontheight;
+ b = t + height * p->fontheight;
+
+ dl = dx * p->fontwidth;
+ dr = dl + width * p->fontwidth;
+ dt = dy * p->fontheight;
+ db = dt + height * p->fontheight;
+
+ /* w is the # pixels between two long-aligned points, left and right */
+ w = (r&~31) - ((l+31)&~31);
+ dw = (dr&~31) - ((dl+31)&~31);
+ /* lo is the # pixels between the left edge and a long-aligned left pixel */
+ lo = ((l+31)&~31) - l;
+ dlo = ((dl+31)&~31) - dl;
+
+ /* if dx != sx then, logic has to align the left and right edges for fast moves */
+ if (lo != dlo) {
+ lo = ((l+7)&~7) - l;
+ dlo = ((dl+7)&~7) - dl;
+ w = (r&~7) - ((l+7)&~7);
+ dw = (dr&~7) - ((dl+7)&~7);
+ if (lo != dlo) {
+ char err_str[256];
+ unsigned long cnt;
+ sprintf( err_str, "ERROR: Shift algorithm: sx=%d,sy=%d,dx=%d,dy=%d,w=%d,h=%d,bpp=%d",
+ sx,sy,dx,dy,width,height,p->var.bits_per_pixel);
+ fbcon_mac_putcs(p->conp, p, err_str, strlen(err_str), 0, 0);
+ /* pause for the user */
+ for(cnt = 0; cnt < 50000; cnt++)
+ udelay(100);
+ return;
+ }
+ }
+
+ s = 0;
+ switch (p->var.bits_per_pixel) {
+ case 1:
+ s = w >> 3;
+ src += lo >> 3;
+ dest += lo >> 3;
+ break;
+ case 2:
+ s = w >> 2;
+ src += lo >> 2;
+ dest += lo >> 2;
+ break;
+ case 4:
+ s = w >> 1;
+ src += lo >> 1;
+ dest += lo >> 1;
+ break;
+ case 8:
+ s = w;
+ src += lo;
+ dest += lo;
+ break;
+ case 16:
+ s = w << 1;
+ src += lo << 1;
+ dest += lo << 1;
+ break;
+ case 32:
+ s = w << 2;
+ src += lo << 2;
+ dest += lo << 2;
+ break;
+ }
+
+ if (sy <= sx) {
+ i = b;
+ move_up = 0;
+ src += height * p->fontheight;
+ dest += height * p->fontheight;
+ } else {
+ i = t;
+ move_up = 1;
+ }
+
+ while (1) {
+ for (i = t; i < b; i++) {
+ j = l;
+
+ for (; j & 31 && j < r; j++)
+ plot_pixel_mac(p, get_pixel_mac(p, j+(dx-sx), i+(dy-sy)), j, i);
+
+ if (j < r) {
+ mymemmove(dest, src, s);
+ if (move_up) {
+ dest += p->next_line;
+ src += p->next_line;
+ } else {
+ dest -= p->next_line;
+ src -= p->next_line;
+ }
+ j += w;
+ }
+
+ for (; j < r; j++)
+ plot_pixel_mac(p, get_pixel_mac(p, j+(dx-sx), i+(dy-sy)), j, i);
+ }
+
+ if (move_up) {
+ i++;
+ if (i >= b)
+ break;
+ } else {
+ i--;
+ if (i < t)
+ break;
+ }
+ }
+}
+
+
+void fbcon_mac_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
+{
+ int pixel;
+ int i, j;
+ int inverse;
+ u8 *dest;
+ int l,r,t,b,w,lo,s;
+
+ inverse = attr_reverse(p,conp);
+ pixel = inverse ? PIXEL_WHITE_MAC : PIXEL_BLACK_MAC;
+ dest = (u8 *) (p->screen_base + sy * p->fontheight * p->next_line);
+
+ if( sx == 0 && width == p->conp->vc_cols) {
+ s = height * p->fontheight * p->next_line;
+ if (inverse)
+ mymemclear(dest, s);
+ else
+ mymemset(dest, s);
+ }
+
+ l = sx * p->fontwidth;
+ r = l + width * p->fontwidth;
+ t = sy * p->fontheight;
+ b = t + height * p->fontheight;
+ /* w is the # pixels between two long-aligned points, left and right */
+ w = (r&~31) - ((l+31)&~31);
+ /* lo is the # pixels between the left edge and a long-aligned left pixel */
+ lo = ((l+31)&~31) - l;
+ s = 0;
+ switch (p->var.bits_per_pixel) {
+ case 1:
+ s = w >> 3;
+ dest += lo >> 3;
+ break;
+ case 2:
+ s = w >> 2;
+ dest += lo >> 2;
+ break;
+ case 4:
+ s = w >> 1;
+ dest += lo >> 1;
+ break;
+ case 8:
+ s = w;
+ dest += lo;
+ break;
+ case 16:
+ s = w << 1;
+ dest += lo << 1;
+ break;
+ case 32:
+ s = w << 2;
+ dest += lo << 2;
+ break;
+ }
+
+ for (i = t; i < b; i++) {
+ j = l;
+
+ for (; j & 31 && j < r; j++)
+ plot_pixel_mac(p, pixel, j, i);
+
+ if (j < r) {
+ if (PIXEL_WHITE_MAC == pixel)
+ mymemclear(dest, s);
+ else
+ mymemset(dest, s);
+ dest += p->next_line;
+ j += w;
+ }
+
+ for (; j < r; j++)
+ plot_pixel_mac(p, pixel, j, i);
+ }
+}
+
+
+void fbcon_mac_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
+{
+ u8 *cdat;
+ u_int rows, bold, ch_reverse, ch_underline;
+ u8 d;
+ int j;
+
+ c &= 0xff;
+
+ cdat = p->fontdata+c*p->fontheight;
+ bold = attr_bold(p,conp);
+ ch_reverse = attr_reverse(p,conp);
+ ch_underline = attr_underline(p,conp);
+
+ for (rows = 0; rows < p->fontheight; rows++) {
+ d = *cdat++;
+ if (!conp->vc_can_do_color) {
+ if (ch_underline && rows == (p->fontheight-2))
+ d = 0xff;
+ else if (bold)
+ d |= d>>1;
+ if (ch_reverse)
+ d = ~d;
+ }
+ for (j = 0; j < p->fontwidth; j++) {
+ plot_pixel_mac(p, (d & 0x80) >> 7, (xx*p->fontwidth) + j, (yy*p->fontheight) + rows);
+ d <<= 1;
+ }
+ }
+}
+
+
+void fbcon_mac_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
+{
+ u8 c;
+
+ while (count--) {
+ c = *s++;
+ fbcon_mac_putc(conp, p, c, yy, xx++);
+ }
+}
+
+
+void fbcon_mac_revc(struct display *p, int xx, int yy)
+{
+ u_int rows, j;
+
+ for (rows = 0; rows < p->fontheight; rows++) {
+ for (j = 0; j < p->fontwidth; j++) {
+ plot_pixel_mac (p, PIXEL_INVERT_MAC, (xx*p->fontwidth)+j, (yy*p->fontheight)+rows);
+ }
+ }
+}
+
+/*
+ * plot_pixel_mac
+ *
+ * bw == 0 = black
+ * 1 = white
+ * 2 = invert
+ */
+static void plot_pixel_mac(struct display *p, int bw, int pixel_x, int pixel_y)
+{
+ u8 *dest, bit;
+ u16 *dest16, pix16;
+ u32 *dest32, pix32;
+
+ if (pixel_x < 0 || pixel_y < 0 || pixel_x >= 832 || pixel_y >= 624) {
+ int cnt;
+ printk ("ERROR: pixel_x == %d, pixel_y == %d", pixel_x, pixel_y);
+ for(cnt = 0; cnt < 100000; cnt++)
+ udelay(100);
+ return;
+ }
+
+ switch (p->var.bits_per_pixel) {
+ case 1:
+ dest = (u8 *) ((pixel_x >> 3) + p->screen_base + pixel_y * p->next_line);
+ bit = 0x80 >> (pixel_x & 7);
+ switch (bw) {
+ case PIXEL_BLACK_MAC:
+ *dest |= bit;
+ break;
+ case PIXEL_WHITE_MAC:
+ *dest &= ~bit;
+ break;
+ case PIXEL_INVERT_MAC:
+ *dest ^= bit;
+ break;
+ default:
+ printk( "ERROR: Unknown pixel value in plot_pixel_mac\n");
+ }
+ break;
+
+ case 2:
+ dest = (u8 *) ((pixel_x >> 2) + p->screen_base + pixel_y * p->next_line);
+ bit = 0xC0 >> ((pixel_x & 3) << 1);
+ switch (bw) {
+ case PIXEL_BLACK_MAC:
+ *dest |= bit;
+ break;
+ case PIXEL_WHITE_MAC:
+ *dest &= ~bit;
+ break;
+ case PIXEL_INVERT_MAC:
+ *dest ^= bit;
+ break;
+ default:
+ printk( "ERROR: Unknown pixel value in plot_pixel_mac\n");
+ }
+ break;
+
+ case 4:
+ dest = (u8 *) ((pixel_x / 2) + p->screen_base + pixel_y * p->next_line);
+ bit = 0xF0 >> ((pixel_x & 1) << 2);
+ switch (bw) {
+ case PIXEL_BLACK_MAC:
+ *dest |= bit;
+ break;
+ case PIXEL_WHITE_MAC:
+ *dest &= ~bit;
+ break;
+ case PIXEL_INVERT_MAC:
+ *dest ^= bit;
+ break;
+ default:
+ printk( "ERROR: Unknown pixel value in plot_pixel_mac\n");
+ }
+ break;
+
+ case 8:
+ dest = (u8 *) (pixel_x + p->screen_base + pixel_y * p->next_line);
+ bit = 0xFF;
+ switch (bw) {
+ case PIXEL_BLACK_MAC:
+ *dest |= bit;
+ break;
+ case PIXEL_WHITE_MAC:
+ *dest &= ~bit;
+ break;
+ case PIXEL_INVERT_MAC:
+ *dest ^= bit;
+ break;
+ default:
+ printk( "ERROR: Unknown pixel value in plot_pixel_mac\n");
+ }
+ break;
+
+ case 16:
+ dest16 = (u16 *) ((pixel_x *2) + p->screen_base + pixel_y * p->next_line);
+ pix16 = 0xFFFF;
+ switch (bw) {
+ case PIXEL_BLACK_MAC:
+ *dest16 = ~pix16;
+ break;
+ case PIXEL_WHITE_MAC:
+ *dest16 = pix16;
+ break;
+ case PIXEL_INVERT_MAC:
+ *dest16 ^= pix16;
+ break;
+ default:
+ printk( "ERROR: Unknown pixel value in plot_pixel_mac\n");
+ }
+ break;
+
+ case 32:
+ dest32 = (u32 *) ((pixel_x *4) + p->screen_base + pixel_y * p->next_line);
+ pix32 = 0xFFFFFFFF;
+ switch (bw) {
+ case PIXEL_BLACK_MAC:
+ *dest32 = ~pix32;
+ break;
+ case PIXEL_WHITE_MAC:
+ *dest32 = pix32;
+ break;
+ case PIXEL_INVERT_MAC:
+ *dest32 ^= pix32;
+ break;
+ default:
+ printk( "ERROR: Unknown pixel value in plot_pixel_mac\n");
+ }
+ break;
+ }
+}
+
+static int get_pixel_mac(struct display *p, int pixel_x, int pixel_y)
+{
+ u8 *dest, bit;
+ u16 *dest16;
+ u32 *dest32;
+ u8 pixel;
+
+ switch (p->var.bits_per_pixel) {
+ case 1:
+ dest = (u8 *) ((pixel_x / 8) + p->screen_base + pixel_y * p->next_line);
+ bit = 0x80 >> (pixel_x & 7);
+ pixel = *dest & bit;
+ break;
+ case 2:
+ dest = (u8 *) ((pixel_x / 4) + p->screen_base + pixel_y * p->next_line);
+ bit = 0xC0 >> (pixel_x & 3);
+ pixel = *dest & bit;
+ break;
+ case 4:
+ dest = (u8 *) ((pixel_x / 2) + p->screen_base + pixel_y * p->next_line);
+ bit = 0xF0 >> (pixel_x & 1);
+ pixel = *dest & bit;
+ break;
+ case 8:
+ dest = (u8 *) (pixel_x + p->screen_base + pixel_y * p->next_line);
+ pixel = *dest;
+ break;
+ case 16:
+ dest16 = (u16 *) ((pixel_x *2) + p->screen_base + pixel_y * p->next_line);
+ pixel = *dest16 ? 1 : 0;
+ break;
+ case 32:
+ dest32 = (u32 *) ((pixel_x *4) + p->screen_base + pixel_y * p->next_line);
+ pixel = *dest32 ? 1 : 0;
+ break;
+ }
+
+ return pixel ? PIXEL_BLACK_MAC : PIXEL_WHITE_MAC;
+}
+
+
+ /*
+ * `switch' for the low level operations
+ */
+
+struct display_switch fbcon_mac = {
+ fbcon_mac_setup, fbcon_mac_bmove, fbcon_mac_clear, fbcon_mac_putc,
+ fbcon_mac_putcs, fbcon_mac_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_mac);
+EXPORT_SYMBOL(fbcon_mac_setup);
+EXPORT_SYMBOL(fbcon_mac_bmove);
+EXPORT_SYMBOL(fbcon_mac_clear);
+EXPORT_SYMBOL(fbcon_mac_putc);
+EXPORT_SYMBOL(fbcon_mac_putcs);
+EXPORT_SYMBOL(fbcon_mac_revc);
diff --git a/drivers/video/fbcon-mac.h b/drivers/video/fbcon-mac.h
new file mode 100644
index 000000000..7e807cce9
--- /dev/null
+++ b/drivers/video/fbcon-mac.h
@@ -0,0 +1,15 @@
+ /*
+ * Mac variable bpp packed pixels (mac)
+ */
+
+extern struct display_switch fbcon_mac;
+extern void fbcon_mac_setup(struct display *p);
+extern void fbcon_mac_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_mac_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_mac_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_mac_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_mac_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-mfb.c b/drivers/video/fbcon-mfb.c
index 7ac001ab4..3484cef2a 100644
--- a/drivers/video/fbcon-mfb.c
+++ b/drivers/video/fbcon-mfb.c
@@ -13,65 +13,30 @@
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
+#include <linux/config.h>
#include <linux/fb.h>
#include "fbcon.h"
-
-
- /*
- * Prototypes
- */
-
-static int open_mfb(struct display *p);
-static void release_mfb(void);
-static void bmove_mfb(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_mfb(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width);
-static void putc_mfb(struct vc_data *conp, struct display *p, int c, int yy,
- int xx);
-static void putcs_mfb(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx);
-static void rev_char_mfb(struct display *p, int xx, int yy);
-
-
- /*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_mfb = {
- open_mfb, release_mfb, bmove_mfb, clear_mfb, putc_mfb, putcs_mfb,
- rev_char_mfb
-};
+#include "fbcon-mfb.h"
/*
* Monochrome
*/
-static int open_mfb(struct display *p)
+void fbcon_mfb_setup(struct display *p)
{
- if (p->var.bits_per_pixel != 1)
- return -EINVAL;
-
if (p->line_length)
p->next_line = p->line_length;
else
p->next_line = p->var.xres_virtual>>3;
p->next_plane = 0;
- MOD_INC_USE_COUNT;
- return 0;
}
-static void release_mfb(void)
+void fbcon_mfb_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_mfb(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
-{
- u_char *src, *dest;
+ u8 *src, *dest;
u_int rows;
if (sx == 0 && dx == 0 && width == p->next_line) {
@@ -97,10 +62,10 @@ static void bmove_mfb(struct display *p, int sy, int sx, int dy, int dx,
}
}
-static void clear_mfb(struct vc_data *conp, struct display *p, int sy, int sx,
- int height, int width)
+void fbcon_mfb_clear(struct vc_data *conp, struct display *p, int sy, int sx,
+ int height, int width)
{
- u_char *dest;
+ u8 *dest;
u_int rows;
dest = p->screen_base+sy*p->fontheight*p->next_line+sx;
@@ -118,12 +83,12 @@ static void clear_mfb(struct vc_data *conp, struct display *p, int sy, int sx,
mymemclear_small(dest, width);
}
-static void putc_mfb(struct vc_data *conp, struct display *p, int c, int yy,
- int xx)
+void fbcon_mfb_putc(struct vc_data *conp, struct display *p, int c, int yy,
+ int xx)
{
- u_char *dest, *cdat;
+ u8 *dest, *cdat;
u_int rows, bold, revs, underl;
- u_char d;
+ u8 d;
c &= 0xff;
@@ -145,12 +110,12 @@ static void putc_mfb(struct vc_data *conp, struct display *p, int c, int yy,
}
}
-static void putcs_mfb(struct vc_data *conp, struct display *p, const char *s,
- int count, int yy, int xx)
+void fbcon_mfb_putcs(struct vc_data *conp, struct display *p, const char *s,
+ int count, int yy, int xx)
{
- u_char *dest, *dest0, *cdat;
+ u8 *dest, *dest0, *cdat;
u_int rows, bold, revs, underl;
- u_char c, d;
+ u8 c, d;
dest0 = p->screen_base+yy*p->fontheight*p->next_line+xx;
bold = attr_bold(p,conp);
@@ -174,9 +139,9 @@ static void putcs_mfb(struct vc_data *conp, struct display *p, const char *s,
}
}
-static void rev_char_mfb(struct display *p, int xx, int yy)
+void fbcon_mfb_revc(struct display *p, int xx, int yy)
{
- u_char *dest;
+ u8 *dest;
u_int rows;
dest = p->screen_base+yy*p->fontheight*p->next_line+xx;
@@ -185,18 +150,24 @@ static void rev_char_mfb(struct display *p, int xx, int yy)
}
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_mfb(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_mfb, 0));
-}
+ /*
+ * `switch' for the low level operations
+ */
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_mfb);
-}
-#endif /* MODULE */
+struct display_switch fbcon_mfb = {
+ fbcon_mfb_setup, fbcon_mfb_bmove, fbcon_mfb_clear, fbcon_mfb_putc,
+ fbcon_mfb_putcs, fbcon_mfb_revc
+};
+
+
+ /*
+ * Visible symbols for modules
+ */
+
+EXPORT_SYMBOL(fbcon_mfb);
+EXPORT_SYMBOL(fbcon_mfb_setup);
+EXPORT_SYMBOL(fbcon_mfb_bmove);
+EXPORT_SYMBOL(fbcon_mfb_clear);
+EXPORT_SYMBOL(fbcon_mfb_putc);
+EXPORT_SYMBOL(fbcon_mfb_putcs);
+EXPORT_SYMBOL(fbcon_mfb_revc);
diff --git a/drivers/video/fbcon-mfb.h b/drivers/video/fbcon-mfb.h
new file mode 100644
index 000000000..b67d9f70e
--- /dev/null
+++ b/drivers/video/fbcon-mfb.h
@@ -0,0 +1,15 @@
+ /*
+ * Monochrome (mfb)
+ */
+
+extern struct display_switch fbcon_mfb;
+extern void fbcon_mfb_setup(struct display *p);
+extern void fbcon_mfb_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width);
+extern void fbcon_mfb_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width);
+extern void fbcon_mfb_putc(struct vc_data *conp, struct display *p, int c,
+ int yy, int xx);
+extern void fbcon_mfb_putcs(struct vc_data *conp, struct display *p,
+ const char *s, int count, int yy, int xx);
+extern void fbcon_mfb_revc(struct display *p, int xx, int yy);
diff --git a/drivers/video/fbcon-retz3.c b/drivers/video/fbcon-retz3.c
deleted file mode 100644
index 71095a084..000000000
--- a/drivers/video/fbcon-retz3.c
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
- * linux/drivers/video/retz3.c -- Low level frame buffer operations for the
- * RetinaZ3 (accelerated)
- *
- * Created 5 Apr 1997 by Geert Uytterhoeven
- *
- * 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.
- */
-
-#include <linux/module.h>
-#include <linux/tty.h>
-#include <linux/console.h>
-#include <linux/string.h>
-#include <linux/fb.h>
-
-#include "fbcon.h"
-
-
-/*
- * Prototypes
- */
-
-static int open_retz3(struct display *p);
-static void release_retz3(void);
-static void bmove_retz3(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width);
-static void clear_retz3(struct vc_data *conp, struct display *p, int
- sy, int sx, int height, int width);
-static void putc_retz3(struct vc_data *conp, struct display *p, int c,
- int ypos, int xpos);
-static void putcs_retz3(struct vc_data *conp, struct display *p, const
- char *s, int count, int ypos, int xpos);
-static void rev_char_retz3(struct display *p, int xpos, int ypos);
-
-
- /*
- * Acceleration functions in retz3fb.c
- */
-
-extern void retz3_bitblt(struct fb_var_screeninfo *scr,
- unsigned short srcx, unsigned short srcy, unsigned
- short destx, unsigned short desty, unsigned short
- width, unsigned short height, unsigned short cmd,
- unsigned short mask);
-
-#define Z3BLTcopy 0xc0
-#define Z3BLTset 0xf0
-
-
-/*
- * `switch' for the low level operations
- */
-
-static struct display_switch dispsw_retz3 = {
- open_retz3, release_retz3, bmove_retz3, clear_retz3, putc_retz3,
- putcs_retz3, rev_char_retz3
-};
-
-
-/*
- * RetinaZ3 (accelerated)
- */
-
-static int open_retz3(struct display *p)
-{
- if (p->type != FB_TYPE_PACKED_PIXELS ||
- p->var.accel != FB_ACCEL_RETINAZ3)
- return -EINVAL;
-
- p->next_line = p->var.xres_virtual*p->var.bits_per_pixel>>3;
- p->next_plane = 0;
- MOD_INC_USE_COUNT;
- return 0;
-}
-
-static void release_retz3(void)
-{
- MOD_DEC_USE_COUNT;
-}
-
-static void bmove_retz3(struct display *p, int sy, int sx, int dy, int dx,
- int height, int width)
-{
- int fontwidth = p->fontwidth;
-
- sx *= fontwidth;
- dx *= fontwidth;
- width *= fontwidth;
-
- retz3_bitblt(&p->var,
- (unsigned short)sx,
- (unsigned short)(sy*p->fontheight),
- (unsigned short)dx,
- (unsigned short)(dy*p->fontheight),
- (unsigned short)width,
- (unsigned short)(height*p->fontheight),
- Z3BLTcopy,
- 0xffff);
-}
-
-static void clear_retz3(struct vc_data *conp, struct display *p, int
- sy, int sx, int height, int width)
-{
- unsigned short col;
- int fontwidth = p->fontwidth;
-
- sx *= fontwidth;
- width *= fontwidth;
-
- col = attr_bgcol_ec(p, conp);
- col &= 0xff;
- col |= (col << 8);
-
- retz3_bitblt(&p->var,
- (unsigned short)sx,
- (unsigned short)(sy*p->fontheight),
- (unsigned short)sx,
- (unsigned short)(sy*p->fontheight),
- (unsigned short)width,
- (unsigned short)(height*p->fontheight),
- Z3BLTset,
- col);
-}
-
-static void putc_retz3(struct vc_data *conp, struct display *p,
- int c, int ypos, int xpos)
-{
- unsigned char *dest, *cdat;
- unsigned long tmp;
- unsigned int rows, revs, underl;
- unsigned char d;
- unsigned char fg, bg;
-
- c &= 0xff;
-
- dest = p->screen_base + ypos * p->fontheight * p->next_line +
- xpos*p->fontwidth;
- cdat = p->fontdata + c * p->fontheight;
-
- fg = p->fgcol;
- bg = p->bgcol;
- revs = conp->vc_reverse;
- underl = conp->vc_underline;
-
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat++;
-
- if (underl && !rows)
- d = 0xff;
- if (revs)
- d = ~d;
-
- tmp = ((d & 0x80) ? fg : bg) << 24;
- tmp |= ((d & 0x40) ? fg : bg) << 16;
- tmp |= ((d & 0x20) ? fg : bg) << 8;
- tmp |= ((d & 0x10) ? fg : bg);
- *((unsigned long*) dest) = tmp;
- tmp = ((d & 0x8) ? fg : bg) << 24;
- tmp |= ((d & 0x4) ? fg : bg) << 16;
- tmp |= ((d & 0x2) ? fg : bg) << 8;
- tmp |= ((d & 0x1) ? fg : bg);
- *((unsigned long*) dest + 1) = tmp;
- }
-}
-
-static void putcs_retz3(struct vc_data *conp, struct display *p,
- const char *s, int count, int ypos, int xpos)
-{
- unsigned char *dest, *dest0, *cdat;
- unsigned long tmp;
- unsigned int rows, revs, underl;
- unsigned char c, d;
- unsigned char fg, bg;
-
- dest0 = p->screen_base + ypos * p->fontheight * p->next_line
- + xpos * p->fontwidth;
-
- fg = p->fgcol;
- bg = p->bgcol;
- revs = conp->vc_reverse;
- underl = conp->vc_underline;
-
- while (count--) {
- c = *s++;
- dest = dest0;
- dest0 += 8;
-
- cdat = p->fontdata + c * p->fontheight;
- for (rows = p->fontheight; rows--; dest += p->next_line) {
- d = *cdat++;
-
- if (underl && !rows)
- d = 0xff;
- if (revs)
- d = ~d;
-
- tmp = ((d & 0x80) ? fg : bg) << 24;
- tmp |= ((d & 0x40) ? fg : bg) << 16;
- tmp |= ((d & 0x20) ? fg : bg) << 8;
- tmp |= ((d & 0x10) ? fg : bg);
- *((unsigned long*) dest) = tmp;
- tmp = ((d & 0x8) ? fg : bg) << 24;
- tmp |= ((d & 0x4) ? fg : bg) << 16;
- tmp |= ((d & 0x2) ? fg : bg) << 8;
- tmp |= ((d & 0x1) ? fg : bg);
- *((unsigned long*) dest + 1) = tmp;
- }
- }
-}
-
-static void rev_char_retz3(struct display *p, int xpos, int ypos)
-{
- unsigned char *dest;
- int bytes=p->next_line, rows;
- unsigned int bpp, mask;
-
- bpp = p->var.bits_per_pixel;
-
- switch (bpp){
- case 8:
- mask = 0x0f0f0f0f;
- break;
- case 16:
- mask = 0xffffffff;
- break;
- case 24:
- mask = 0xffffffff; /* ??? */
- break;
- default:
- printk("illegal depth for rev_char_retz3(), bpp = %i\n", bpp);
- return;
- }
-
- dest = p->screen_base + ypos * p->fontheight * bytes +
- xpos * p->fontwidth;
-
- for (rows = p->fontheight ; rows-- ; dest += bytes) {
- ((unsigned long *)dest)[0] ^= mask;
- ((unsigned long *)dest)[1] ^= mask;
- }
-}
-
-
-#ifdef MODULE
-int init_module(void)
-#else
-int fbcon_init_retz3(void)
-#endif
-{
- return(fbcon_register_driver(&dispsw_retz3, 1));
-}
-
-#ifdef MODULE
-void cleanup_module(void)
-{
- fbcon_unregister_driver(&dispsw_retz3);
-}
-#endif /* MODULE */
diff --git a/drivers/video/fbcon.c b/drivers/video/fbcon.c
index 872d77928..a41bf081d 100644
--- a/drivers/video/fbcon.c
+++ b/drivers/video/fbcon.c
@@ -28,26 +28,17 @@
* The low level operations for the various display memory organizations are
* now in separate source files.
*
- * Currently only the following organizations are supported:
+ * Currently the following organizations are supported:
*
- * - non-accelerated:
- *
- * o mfb Monochrome
- * o ilbm Interleaved bitplanes ŕ la Amiga
- * o afb Bitplanes ŕ la Amiga
- * o iplan2p[248] Interleaved bitplanes ŕ la Atari (2, 4 and 8 planes)
- * o cfb{8,16} Packed pixels (8 and 16 bpp)
- *
- * - accelerated:
- *
- * o cyber CyberVision64 packed pixels (accelerated)
- * o retz3 Retina Z3 packed pixels (accelerated)
- * o mach64 ATI Mach 64 packed pixels (accelerated)
+ * o afb Amiga bitplanes
+ * o cfb{2,4,8,16,24,32} Packed pixels
+ * o ilbm Amiga interleaved bitplanes
+ * o iplan2p[248] Atari interleaved bitplanes
+ * o mfb Monochrome
*
* To do:
*
* - Implement 16 plane mode (iplan2p16)
- * - Add support for 24/32 bit packed pixels (cfb{24,32})
* - Hardware cursor
*
*
@@ -56,6 +47,8 @@
* more details.
*/
+#undef FBCONDEBUG
+
#define SUPPORT_SCROLLBACK 0
#define FLASHING_CURSOR 1
@@ -65,6 +58,7 @@
#include <linux/sched.h>
#include <linux/fs.h>
#include <linux/kernel.h>
+#include <linux/delay.h> /* MSch: for IRQ probe */
#include <linux/tty.h>
#include <linux/console.h>
#include <linux/string.h>
@@ -74,9 +68,6 @@
#include <linux/vt_kern.h>
#include <linux/selection.h>
#include <linux/init.h>
-#ifdef CONFIG_KMOD
-#include <linux/kmod.h>
-#endif
#include <asm/irq.h>
#include <asm/system.h>
@@ -88,6 +79,9 @@
#ifdef CONFIG_ATARI
#include <asm/atariints.h>
#endif
+#ifdef CONFIG_MAC
+#include <asm/macints.h>
+#endif
#ifdef __mc68000__
#include <asm/machdep.h>
#include <asm/setup.h>
@@ -95,8 +89,14 @@
#include <asm/linux_logo.h>
#include "fbcon.h"
+#include "fbcon-mac.h" /* for 6x11 font on mac */
#include "font.h"
+#ifdef FBCONDEBUG
+# define DPRINTK(fmt, args...) printk(KERN_DEBUG "%s: " fmt, __FUNCTION__ , ## args)
+#else
+# define DPRINTK(fmt, args...)
+#endif
struct display fb_display[MAX_NR_CONSOLES];
@@ -112,6 +112,7 @@ static int cursor_drawn = 0;
/* # VBL ints between cursor state changes */
#define AMIGA_CURSOR_BLINK_RATE (20)
#define ATARI_CURSOR_BLINK_RATE (42)
+#define MAC_CURSOR_BLINK_RATE (32)
#define DEFAULT_CURSOR_BLINK_RATE (20)
static int vbl_cursor_cnt = 0;
@@ -146,26 +147,25 @@ static __inline__ int CURSOR_UNDRAWN(void)
static unsigned long fbcon_startup(unsigned long kmem_start,
const char **display_desc);
static void fbcon_init(struct vc_data *conp);
-static int fbcon_deinit(struct vc_data *conp);
+static void fbcon_deinit(struct vc_data *conp);
static int fbcon_changevar(int con);
-static int fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
+static void fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
int width);
-static int fbcon_putc(struct vc_data *conp, int c, int ypos, int xpos);
-static int fbcon_putcs(struct vc_data *conp, const char *s, int count,
- int ypos, int xpos);
-static int fbcon_cursor(struct vc_data *conp, int mode);
-static int fbcon_scroll(struct vc_data *conp, int t, int b,
- int dir, int count);
-static int fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
- int height, int width);
+static void fbcon_putc(struct vc_data *conp, int c, int ypos, int xpos);
+static void fbcon_putcs(struct vc_data *conp, const char *s, int count,
+ int ypos, int xpos);
+static void fbcon_cursor(struct vc_data *conp, int mode);
+static void fbcon_scroll(struct vc_data *conp, int t, int b, int dir,
+ int count);
+static void fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
+ int height, int width);
static int fbcon_switch(struct vc_data *conp);
static int fbcon_blank(int blank);
static int fbcon_get_font(struct vc_data *conp, int *w, int *h, char *data);
static int fbcon_set_font(struct vc_data *conp, int w, int h, char *data);
static int fbcon_set_palette(struct vc_data *conp, unsigned char *table);
static int fbcon_scrolldelta(int lines);
-int fbcon_register_driver(struct display_switch *dispsw, int is_accel);
-int fbcon_unregister_driver(struct display_switch *dispsw);
+static int fbcon_set_mode(struct vc_data *conp, int mode);
/*
@@ -193,16 +193,23 @@ static __inline__ void ypan_down(int unit, struct vc_data *conp,
struct display *p, int count);
static void fbcon_bmove_rec(struct display *p, int sy, int sx, int dy, int dx,
int height, int width, u_int y_break);
-static struct display_switch *probe_list(struct display_switch *dispsw,
- struct display *disp);
-#ifdef CONFIG_KMOD
-static void request_driver(struct display *disp, int is_accel);
-#endif
-static struct display_switch *fbcon_get_driver(struct display *disp);
static int fbcon_show_logo(void);
#if FLASHING_CURSOR
+
+#ifdef CONFIG_MAC
+/*
+ * On the Macintoy, there may or may not be a working VBL int. We need to prob
+ */
+static int vbl_detected = 0;
+
+static void fbcon_vbl_detect(int irq, void *dummy, struct pt_regs *fp)
+{
+ vbl_detected++;
+}
+#endif
+
static void cursor_timer_handler(unsigned long dev_addr);
static struct timer_list cursor_timer = {
@@ -212,7 +219,7 @@ static struct timer_list cursor_timer = {
static void cursor_timer_handler(unsigned long dev_addr)
{
fbcon_vbl_handler(0, NULL, NULL);
- cursor_timer.expires = jiffies+2;
+ cursor_timer.expires = jiffies+HZ/50;
cursor_timer.data = 0;
cursor_timer.next = cursor_timer.next = NULL;
add_timer(&cursor_timer);
@@ -223,49 +230,8 @@ static void cursor_timer_handler(unsigned long dev_addr)
* Low Level Operations
*/
-static struct display_switch dispsw_dummy;
+static struct display_switch fbcon_dummy;
-#ifdef CONFIG_FBCON_MFB
-extern int fbcon_init_mfb(void);
-#endif
-#ifdef CONFIG_FBCON_ILBM
-extern int fbcon_init_ilbm(void);
-#endif
-#ifdef CONFIG_FBCON_AFB
-extern int fbcon_init_afb(void);
-#endif
-#ifdef CONFIG_FBCON_IPLAN2P2
-extern int fbcon_init_iplan2p2(void);
-#endif
-#ifdef CONFIG_FBCON_IPLAN2P4
-extern int fbcon_init_iplan2p4(void);
-#endif
-#ifdef CONFIG_FBCON_IPLAN2P8
-extern int fbcon_init_iplan2p8(void);
-#endif
-#ifdef CONFIG_FBCON_CFB8
-extern int fbcon_init_cfb8(void);
-#endif
-#ifdef CONFIG_FBCON_CFB16
-extern int fbcon_init_cfb16(void);
-#endif
-#ifdef CONFIG_FBCON_CFB24
-extern int fbcon_init_cfb24(void);
-#endif
-#ifdef CONFIG_FBCON_CFB32
-extern int fbcon_init_cfb32(void);
-#endif
-#ifdef CONFIG_FBCON_CYBER
-extern int fbcon_init_cyber(void);
-#endif
-#ifdef CONFIG_FBCON_RETINAZ3
-extern int fbcon_init_retz3(void);
-#endif
-#ifdef CONFIG_FBCON_MACH64
-extern int fbcon_init_mach64(void);
-#endif
-
-extern int num_registered_fb;
__initfunc(static unsigned long fbcon_startup(unsigned long kmem_start,
const char **display_desc))
@@ -275,49 +241,10 @@ __initfunc(static unsigned long fbcon_startup(unsigned long kmem_start,
/* Probe all frame buffer devices */
kmem_start = probe_framebuffers(kmem_start);
- if (!num_registered_fb)
+ if (!num_registered_fb) {
+ DPRINTK("no framebuffer registered\n");
return kmem_start;
-
- /* Initialize all built-in low level drivers */
-#ifdef CONFIG_FBCON_RETINAZ3
- fbcon_init_retz3();
-#endif
-#ifdef CONFIG_FBCON_MFB
- fbcon_init_mfb();
-#endif
-#ifdef CONFIG_FBCON_IPLAN2P2
- fbcon_init_iplan2p2();
-#endif
-#ifdef CONFIG_FBCON_IPLAN2P4
- fbcon_init_iplan2p4();
-#endif
-#ifdef CONFIG_FBCON_IPLAN2P8
- fbcon_init_iplan2p8();
-#endif
-#ifdef CONFIG_FBCON_ILBM
- fbcon_init_ilbm();
-#endif
-#ifdef CONFIG_FBCON_AFB
- fbcon_init_afb();
-#endif
-#ifdef CONFIG_FBCON_CFB8
- fbcon_init_cfb8();
-#endif
-#ifdef CONFIG_FBCON_CFB16
- fbcon_init_cfb16();
-#endif
-#ifdef CONFIG_FBCON_CFB24
- fbcon_init_cfb24();
-#endif
-#ifdef CONFIG_FBCON_CFB32
- fbcon_init_cfb32();
-#endif
-#ifdef CONFIG_FBCON_CYBER
- fbcon_init_cyber();
-#endif
-#ifdef CONFIG_FBCON_MACH64
- fbcon_init_mach64();
-#endif
+ }
*display_desc = "frame buffer device";
@@ -335,9 +262,49 @@ __initfunc(static unsigned long fbcon_startup(unsigned long kmem_start,
"console/cursor", fbcon_vbl_handler);
}
#endif /* CONFIG_ATARI */
+
+#ifdef CONFIG_MAC
+ /*
+ * On a Macintoy, the VBL interrupt may or may not be active.
+ * As interrupt based cursor is more reliable and race free, we
+ * probe for VBL interrupts.
+ */
+ if (MACH_IS_MAC) {
+ int ct = 0;
+ /*
+ * Probe for VBL: set temp. handler ...
+ */
+ irqres = request_irq(IRQ_MAC_VBL, fbcon_vbl_detect, 0,
+ "console/cursor", fbcon_vbl_detect);
+ /*
+ * ... and spin for 20 ms ...
+ */
+ while (!vbl_detected && ++ct<1000)
+ udelay(20);
+
+ if(ct==1000)
+ printk("fbcon_startup: No VBL detected, using timer based cursor.\n");
+
+ if (vbl_detected) {
+ /*
+ * interrupt based cursor ok
+ */
+ cursor_blink_rate = MAC_CURSOR_BLINK_RATE;
+ irqres = request_irq(IRQ_MAC_VBL, fbcon_vbl_handler, 0,
+ "console/cursor", fbcon_vbl_handler);
+ } else {
+ /*
+ * VBL not detected: fall through, use timer based cursor
+ */
+ irqres = 1;
+ /* free interrupt here ?? */
+ }
+ }
+#endif /* CONFIG_MAC */
+
if (irqres) {
cursor_blink_rate = DEFAULT_CURSOR_BLINK_RATE;
- cursor_timer.expires = jiffies+2;
+ cursor_timer.expires = jiffies+HZ/50;
cursor_timer.data = 0;
cursor_timer.next = cursor_timer.prev = NULL;
add_timer(&cursor_timer);
@@ -360,22 +327,24 @@ static void fbcon_init(struct vc_data *conp)
info->changevar = &fbcon_changevar;
fb_display[unit] = *(info->disp); /* copy from default */
+ DPRINTK("mode: %s\n",info->modename);
+ DPRINTK("visual: %d\n",fb_display[unit].visual);
+ DPRINTK("res: %dx%d-%d\n",fb_display[unit].var.xres,
+ fb_display[unit].var.yres,
+ fb_display[unit].var.bits_per_pixel);
fb_display[unit].conp = conp;
fb_display[unit].fb_info = info;
fbcon_setup(unit, 1, 1);
}
-static int fbcon_deinit(struct vc_data *conp)
+static void fbcon_deinit(struct vc_data *conp)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
- if (p->dispsw)
- p->dispsw->release();
- p->dispsw = 0;
+ p->dispsw = NULL;
p->conp = 0;
- return(0);
}
@@ -405,7 +374,6 @@ static void fbcon_setup(int con, int setcol, int init)
struct display *p = &fb_display[con];
struct vc_data *conp = p->conp;
int nr_rows, nr_cols;
- struct display_switch *old_dispsw, *new_dispsw;
p->var.xoffset = p->var.yoffset = p->yscroll = 0; /* reset wrap/pan */
@@ -415,9 +383,17 @@ static void fbcon_setup(int con, int setcol, int init)
getdefaultfont(p->var.xres, p->var.yres, NULL, &p->fontwidth,
&p->fontheight, &p->fontdata);
if (p->fontwidth != 8) {
- /* ++Geert: changed from panic() to `correct and continue' */
- printk(KERN_ERR "fbcon_setup: No support for fontwidth != 8");
- p->fontwidth = 8;
+#ifdef CONFIG_MAC
+ if (MACH_IS_MAC)
+ /* ++Geert: hack to make 6x11 fonts work on mac */
+ p->dispsw = &fbcon_mac;
+ else
+#endif
+ {
+ /* ++Geert: changed from panic() to `correct and continue' */
+ printk(KERN_ERR "fbcon_setup: No support for fontwidth != 8");
+ p->dispsw = &fbcon_dummy;
+ }
}
updatescrollmode(p);
@@ -435,18 +411,12 @@ static void fbcon_setup(int con, int setcol, int init)
p->vrows = p->var.yres_virtual/p->fontheight;
conp->vc_can_do_color = p->var.bits_per_pixel != 1;
- new_dispsw = fbcon_get_driver(p);
- if (!new_dispsw) {
+ if (!p->dispsw) {
printk(KERN_WARNING "fbcon_setup: type %d (aux %d, depth %d) not "
"supported\n", p->type, p->type_aux, p->var.bits_per_pixel);
- dispsw_dummy.open(p);
- new_dispsw = &dispsw_dummy;
+ p->dispsw = &fbcon_dummy;
}
- /* Be careful when changing dispsw, it might be the current console. */
- old_dispsw = p->dispsw;
- p->dispsw = new_dispsw;
- if (old_dispsw)
- old_dispsw->release();
+ p->dispsw->setup(p);
if (setcol) {
p->fgcol = p->var.bits_per_pixel > 2 ? 7 : (1<<p->var.bits_per_pixel)-1;
@@ -492,15 +462,18 @@ static __inline__ int real_y(struct display *p, int ypos)
}
-static int fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
- int width)
+static void fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
+ int width)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
u_int y_break;
if (!p->can_soft_blank && console_blanked)
- return(0);
+ return;
+
+ if (!height || !width)
+ return;
if ((sy <= p->cursor_y) && (p->cursor_y < sy+height) &&
(sx <= p->cursor_x) && (p->cursor_x < sx+width))
@@ -515,47 +488,41 @@ static int fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
p->dispsw->clear(conp, p, real_y(p, sy+b), sx, height-b, width);
} else
p->dispsw->clear(conp, p, real_y(p, sy), sx, height, width);
-
- return(0);
}
-static int fbcon_putc(struct vc_data *conp, int c, int ypos, int xpos)
+static void fbcon_putc(struct vc_data *conp, int c, int ypos, int xpos)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
if (!p->can_soft_blank && console_blanked)
- return 0;
+ return;
if ((p->cursor_x == xpos) && (p->cursor_y == ypos))
CURSOR_UNDRAWN();
p->dispsw->putc(conp, p, c, real_y(p, ypos), xpos);
-
- return 0;
}
-static int fbcon_putcs(struct vc_data *conp, const char *s, int count,
+static void fbcon_putcs(struct vc_data *conp, const char *s, int count,
int ypos, int xpos)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
if (!p->can_soft_blank && console_blanked)
- return 0;
+ return;
if ((p->cursor_y == ypos) && (xpos <= p->cursor_x) &&
(p->cursor_x < (xpos + count)))
CURSOR_UNDRAWN();
p->dispsw->putcs(conp, p, s, count, real_y(p, ypos), xpos);
-
- return(0);
}
-static int fbcon_cursor(struct vc_data *conp, int mode)
+static void fbcon_cursor(struct vc_data *conp, int mode)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
@@ -563,9 +530,9 @@ static int fbcon_cursor(struct vc_data *conp, int mode)
/* Avoid flickering if there's no real change. */
if (p->cursor_x == conp->vc_x && p->cursor_y == conp->vc_y &&
(mode == CM_ERASE) == !cursor_on)
- return 0;
+ return;
if (CURSOR_UNDRAWN ())
- p->dispsw->rev_char(p, p->cursor_x, real_y(p, p->cursor_y));
+ p->dispsw->revc(p, p->cursor_x, real_y(p, p->cursor_y));
p->cursor_x = conp->vc_x;
p->cursor_y = conp->vc_y;
@@ -580,8 +547,6 @@ static int fbcon_cursor(struct vc_data *conp, int mode)
cursor_on = 1;
break;
}
-
- return(0);
}
@@ -598,7 +563,7 @@ static void fbcon_vbl_handler(int irq, void *dummy, struct pt_regs *fp)
* switching code should set vbl_cursor_cnt to an appropriate value.
*/
p = &fb_display[fg_console];
- p->dispsw->rev_char(p, p->cursor_x, real_y(p, p->cursor_y));
+ p->dispsw->revc(p, p->cursor_x, real_y(p, p->cursor_y));
cursor_drawn ^= 1;
vbl_cursor_cnt = cursor_blink_rate;
}
@@ -623,7 +588,7 @@ static __inline__ void ywrap_up(int unit, struct display *p, int count)
p->var.xoffset = 0;
p->var.yoffset = p->yscroll*p->fontheight;
p->var.vmode |= FB_VMODE_YWRAP;
- p->fb_info->updatevar(unit);
+ p->fb_info->updatevar(unit, p->fb_info);
#if SUPPORT_SCROLLBACK
scrollback_max += count;
if (scrollback_max > p->vrows-conp->vc_rows)
@@ -646,7 +611,7 @@ static __inline__ void ywrap_down(int unit, struct display *p, int count)
p->var.xoffset = 0;
p->var.yoffset = p->yscroll*p->fontheight;
p->var.vmode |= FB_VMODE_YWRAP;
- p->fb_info->updatevar(unit);
+ p->fb_info->updatevar(unit, p->fb_info);
#if SUPPORT_SCROLLBACK
scrollback_max -= count;
if (scrollback_max < 0)
@@ -668,7 +633,7 @@ static __inline__ void ypan_up(int unit, struct vc_data *conp,
p->var.xoffset = 0;
p->var.yoffset = p->yscroll*p->fontheight;
p->var.vmode &= ~FB_VMODE_YWRAP;
- p->fb_info->updatevar(unit);
+ p->fb_info->updatevar(unit, p->fb_info);
}
@@ -684,17 +649,21 @@ static __inline__ void ypan_down(int unit, struct vc_data *conp,
p->var.xoffset = 0;
p->var.yoffset = p->yscroll*p->fontheight;
p->var.vmode &= ~FB_VMODE_YWRAP;
- p->fb_info->updatevar(unit);
+ p->fb_info->updatevar(unit, p->fb_info);
}
-static int fbcon_scroll(struct vc_data *conp, int t, int b, int dir, int count)
+static void fbcon_scroll(struct vc_data *conp, int t, int b, int dir,
+ int count)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
if (!p->can_soft_blank && console_blanked)
- return(0);
+ return;
+
+ if (!count)
+ return;
fbcon_cursor(conp, CM_ERASE);
@@ -822,19 +791,20 @@ static int fbcon_scroll(struct vc_data *conp, int t, int b, int dir, int count)
fbcon_clear(conp, 0, t, conp->vc_rows, count);
break;
}
-
- return(0);
}
-static int fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
- int height, int width)
+static void fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
+ int height, int width)
{
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
if (!p->can_soft_blank && console_blanked)
- return(0);
+ return;
+
+ if (!width || !height)
+ return;
if (((sy <= p->cursor_y) && (p->cursor_y < sy+height) &&
(sx <= p->cursor_x) && (p->cursor_x < sx+width)) ||
@@ -850,8 +820,6 @@ static int fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
* over again, so we use fbcon_bmove_rec()
*/
fbcon_bmove_rec(p, sy, sx, dy, dx, height, width, p->vrows-p->yscroll);
-
- return(0);
}
@@ -894,7 +862,7 @@ static int fbcon_switch(struct vc_data *conp)
struct fb_info *info = p->fb_info;
if (info && info->switch_con)
- (*info->switch_con)(conp->vc_num);
+ (*info->switch_con)(conp->vc_num, info);
#if SUPPORT_SCROLLBACK
scrollback_max = 0;
scrollback_current = 0;
@@ -906,11 +874,19 @@ static int fbcon_switch(struct vc_data *conp)
static int fbcon_blank(int blank)
{
struct display *p = &fb_display[fg_console];
+ struct fb_info *info = p->fb_info;
fbcon_cursor(p->conp, blank ? CM_ERASE : CM_DRAW);
if (!p->can_soft_blank) {
if (blank) {
+#ifdef CONFIG_MAC
+ if (MACH_IS_MAC)
+ mymemset(p->screen_base,
+ p->var.xres_virtual*p->var.yres_virtual*
+ p->var.bits_per_pixel>>3);
+ else
+#endif
if (p->visual == FB_VISUAL_MONO01)
mymemset(p->screen_base,
p->var.xres_virtual*p->var.yres_virtual*
@@ -925,7 +901,7 @@ static int fbcon_blank(int blank)
return(1);
}
}
- (*p->fb_info->blank)(blank);
+ (*info->blank)(blank, info);
return(0);
}
@@ -975,7 +951,7 @@ static int fbcon_set_font(struct vc_data *conp, int w, int h, char *data)
copy_from_user( name, data, MAX_FONT_NAME );
name[sizeof(name)-1] = 0;
- if (!findsoftfont( name, &w, &h, (u_char **)&data ))
+ if (!findsoftfont( name, &w, &h, (u8 **)&data ))
return( -ENOENT );
userspace = 0;
} else if (w == 1) {
@@ -1049,9 +1025,9 @@ activate:
return( 0 );
}
-static unsigned short palette_red[16];
-static unsigned short palette_green[16];
-static unsigned short palette_blue[16];
+static u16 palette_red[16];
+static u16 palette_green[16];
+static u16 palette_blue[16];
static struct fb_cmap palette_cmap = {
0, 16, palette_red, palette_green, palette_blue, NULL
@@ -1062,7 +1038,7 @@ static int fbcon_set_palette(struct vc_data *conp, unsigned char *table)
int unit = conp->vc_num;
struct display *p = &fb_display[unit];
int i, j, k;
- u_char val;
+ u8 val;
if (!conp->vc_can_do_color || (!p->can_soft_blank && console_blanked))
return(-EINVAL);
@@ -1078,7 +1054,7 @@ static int fbcon_set_palette(struct vc_data *conp, unsigned char *table)
palette_cmap.len = 1<<p->var.bits_per_pixel;
if (palette_cmap.len > 16)
palette_cmap.len = 16;
- return(p->fb_info->setcmap(&palette_cmap, unit));
+ return p->fb_info->fbops->fb_set_cmap(&palette_cmap, 1, unit, p->fb_info);
}
static int fbcon_scrolldelta(int lines)
@@ -1109,13 +1085,27 @@ static int fbcon_scrolldelta(int lines)
p->var.vmode |= FB_VMODE_YWRAP;
p->var.xoffset = 0;
p->var.yoffset = offset*p->fontheight;
- p->fb_info->updatevar(unit);
+ p->fb_info->updatevar(unit, p->fb_info);
#else
return -ENOSYS;
#endif
}
+ /*
+ * Switch between `text' (emulated and accelerated) and `graphics'
+ * (unaccelerated text) mode
+ */
+
+static int fbcon_set_mode(struct vc_data *conp, int mode)
+{
+ struct display *p = &fb_display[conp->vc_num];
+ struct fb_ops *ops = p->fb_info->fbops;
+
+ return ops->fb_set_mode ? ops->fb_set_mode(mode, p->fb_info) : 0;
+}
+
+
#define LOGO_H 80
#define LOGO_W 80
#define LOGO_LINE (LOGO_W/8)
@@ -1166,7 +1156,8 @@ __initfunc(static int fbcon_show_logo( void ))
palette_cmap.green[j] = (green[i+j] << 8) | green[i+j];
palette_cmap.blue[j] = (blue[i+j] << 8) | blue[i+j];
}
- p->fb_info->setcmap( &palette_cmap, fg_console );
+ p->fb_info->fbops->fb_set_cmap(&palette_cmap, 1, fg_console,
+ p->fb_info);
}
fb_display[fg_console].cmap.len = old_cmap_len;
}
@@ -1184,12 +1175,65 @@ __initfunc(static int fbcon_show_logo( void ))
logo_depth = 1;
}
-#if defined(CONFIG_FBCON_CFB16) || defined(CONFIG_FBCON_CYBER) || \
- defined(CONFIG_FBCON_RETINAZ3)
- if ((depth % 8 == 0) && (p->visual == FB_VISUAL_TRUECOLOR ||
- p->visual == FB_VISUAL_DIRECTCOLOR)) {
+#if defined(CONFIG_FBCON_CFB16) || defined(CONFIG_FBCON_CFB24) || \
+ defined(CONFIG_FBCON_CFB32)
+ if (p->visual == FB_VISUAL_TRUECOLOR) {
+ unsigned int val; /* max. depth 32! */
+ int bdepth;
+ int redshift, greenshift, blueshift;
+
+ /* Bug: Doesn't obey msb_right ... (who needs that?) */
+ redshift = p->var.red.offset;
+ greenshift = p->var.green.offset;
+ blueshift = p->var.blue.offset;
+
+ if (depth >= 24 && (depth % 8) == 0) {
+ /* have at least 8 bits per color */
+ src = logo;
+ bdepth = depth/8;
+ for( y1 = 0; y1 < LOGO_H; y1++ ) {
+ dst = fb + y1*line;
+ for( x1 = 0; x1 < LOGO_W; x1++, src++ ) {
+ val = ((linux_logo_red[*src] & redmask) << redshift) |
+ ((linux_logo_green[*src] & greenmask) << greenshift) |
+ ((linux_logo_blue[*src] & bluemask) << blueshift);
+ for( i = bdepth-1; i >= 0; --i )
+ *dst++ = val >> (i*8);
+ }
+ }
+ }
+ else if (depth >= 15 && depth <= 23) {
+ /* have 5..7 bits per color, using 16 color image */
+ unsigned int pix;
+ src = linux_logo16;
+ bdepth = (depth+7)/8;
+ for( y1 = 0; y1 < LOGO_H; y1++ ) {
+ dst = fb + y1*line;
+ for( x1 = 0; x1 < LOGO_W/2; x1++, src++ ) {
+ pix = (*src >> 4) | 0x10; /* upper nibble */
+ val = (pix << redshift) |
+ (pix << greenshift) |
+ (pix << blueshift);
+ for( i = 0; i < bdepth; ++i )
+ *dst++ = val >> (i*8);
+ pix = (*src & 0x0f) | 0x10; /* lower nibble */
+ val = (pix << redshift) |
+ (pix << greenshift) |
+ (pix << blueshift);
+ for( i = bdepth-1; i >= 0; --i )
+ *dst++ = val >> (i*8);
+ }
+ }
+ }
+
+ done = 1;
+ }
+#endif
+#if defined(CONFIG_FBCON_CFB16) || defined(CONFIG_FBCON_CFB24) || \
+ defined(CONFIG_FBCON_CFB32)
+ if ((depth % 8 == 0) && (p->visual == FB_VISUAL_DIRECTCOLOR)) {
/* Modes without color mapping, needs special data transformation... */
- unsigned long val; /* max. depth 32! */
+ unsigned int val; /* max. depth 32! */
int bdepth = depth/8;
unsigned char mask[9] = { 0,0x80,0xc0,0xe0,0xf0,0xf8,0xfc,0xfe,0xff };
unsigned char redmask, greenmask, bluemask;
@@ -1218,8 +1262,7 @@ __initfunc(static int fbcon_show_logo( void ))
done = 1;
}
#endif
-#if defined(CONFIG_FBCON_CFB8) || defined(CONFIG_FBCON_CYBER) || \
- defined(CONFIG_FBCON_RETINAZ3)
+#if defined(CONFIG_FBCON_CFB8)
if (depth == 8 && p->type == FB_TYPE_PACKED_PIXELS) {
/* depth 8 or more, packed, with color registers */
@@ -1316,153 +1359,23 @@ struct consw fb_con = {
fbcon_startup, fbcon_init, fbcon_deinit, fbcon_clear, fbcon_putc,
fbcon_putcs, fbcon_cursor, fbcon_scroll, fbcon_bmove, fbcon_switch,
fbcon_blank, fbcon_get_font, fbcon_set_font, fbcon_set_palette,
- fbcon_scrolldelta
+ fbcon_scrolldelta, fbcon_set_mode
};
/*
- * Driver registration
- */
-
-static struct display_switch *drivers = NULL, *accel_drivers = NULL;
-
-int fbcon_register_driver(struct display_switch *dispsw, int is_accel)
-{
- struct display_switch **list;
-
- list = is_accel ? &accel_drivers : &drivers;
- dispsw->next = *list;
- *list = dispsw;
- return 0;
-}
-
-int fbcon_unregister_driver(struct display_switch *dispsw)
-{
- struct display_switch **list;
-
- for (list = &accel_drivers; *list; list = &(*list)->next)
- if (*list == dispsw) {
- *list = dispsw->next;
- dispsw->next = NULL;
- return 0;
- }
- for (list = &drivers; *list; list = &(*list)->next)
- if (*list == dispsw) {
- *list = dispsw->next;
- dispsw->next = NULL;
- return 0;
- }
- return -EINVAL;
-}
-
-
-static struct display_switch *probe_list(struct display_switch *dispsw,
- struct display *disp)
-{
- while (dispsw) {
- if (!dispsw->open(disp))
- return(dispsw);
- dispsw = dispsw->next;
- }
- return(NULL);
-}
-
-
-#ifdef CONFIG_KMOD
-static void request_driver(struct display *disp, int is_accel)
-{
- char modname[30];
- int len;
- const char *type;
-
- if (disp->var.bits_per_pixel == 1)
- type = "mfb";
- else
- switch (disp->type) {
- case FB_TYPE_INTERLEAVED_PLANES:
- if (disp->type_aux == 2)
- type = "iplan2p%d";
- else
- type = "ilbm";
- break;
- case FB_TYPE_PLANES:
- type = "afb";
- break;
- case FB_TYPE_PACKED_PIXELS:
- type = "cfb%d";
- break;
- default:
- return;
- }
- len = sprintf(modname, "fbcon-");
- len += sprintf(modname+len, type, disp->var.bits_per_pixel);
- if (is_accel)
- len += sprintf(modname+len, "-%d", disp->var.accel);
- request_module(modname);
-}
-#endif /* CONFIG_KMOD */
-
-
-static struct display_switch *fbcon_get_driver(struct display *disp)
-{
- struct display_switch *dispsw;
-
- if (disp->var.accel != FB_ACCEL_NONE) {
- /* First try an accelerated driver */
- dispsw = probe_list(accel_drivers, disp);
-#ifdef CONFIG_KMOD
- if (!dispsw) {
- request_driver(disp, 1);
- dispsw = probe_list(accel_drivers, disp);
- }
-#endif
- if (dispsw)
- return(dispsw);
- }
-
- /* Then try an unaccelerated driver */
- dispsw = probe_list(drivers, disp);
-#ifdef CONFIG_KMOD
- if (!dispsw) {
- request_driver(disp, 0);
- dispsw = probe_list(drivers, disp);
- }
-#endif
- return(dispsw);
-}
-
-
-/*
* Dummy Low Level Operations
*/
-static int open_dummy(struct display *p)
-{
- if (p->line_length)
- p->next_line = p->line_length;
- else
- p->next_line = p->var.xres_virtual>>3;
- p->next_plane = 0;
- p->var.bits_per_pixel = 1;
- return 0;
-}
+static void fbcon_dummy_op(void) {}
-static void misc_dummy(void) {}
-
-static struct display_switch dispsw_dummy = {
- open_dummy,
- /* release_dummy */
- misc_dummy,
- /* bmove_dummy */
- (void (*)(struct display *, int, int, int, int, int, int))misc_dummy,
- /* clear_dummy */
- (void (*)(struct vc_data *, struct display *, int, int, int, int))misc_dummy,
- /* putc_dummy */
- (void (*)(struct vc_data *, struct display *, int, int, int))misc_dummy,
- /* putcs_dummy */
- (void (*)(struct vc_data *, struct display *, const char *, int, int, int))misc_dummy,
- /* rev_char_dummy */
- (void (*)(struct display *, int, int))misc_dummy,
+static struct display_switch fbcon_dummy = {
+ (void *)fbcon_dummy_op, /* fbcon_dummy_setup */
+ (void *)fbcon_dummy_op, /* fbcon_dummy_bmove */
+ (void *)fbcon_dummy_op, /* fbcon_dummy_clear */
+ (void *)fbcon_dummy_op, /* fbcon_dummy_putc */
+ (void *)fbcon_dummy_op, /* fbcon_dummy_putcs */
+ (void *)fbcon_dummy_op, /* fbcon_dummy_revc */
};
@@ -1471,5 +1384,3 @@ static struct display_switch dispsw_dummy = {
*/
EXPORT_SYMBOL(fb_display);
-EXPORT_SYMBOL(fbcon_register_driver);
-EXPORT_SYMBOL(fbcon_unregister_driver);
diff --git a/drivers/video/fbcon.h b/drivers/video/fbcon.h
index b83376d9e..4868b7730 100644
--- a/drivers/video/fbcon.h
+++ b/drivers/video/fbcon.h
@@ -8,6 +8,9 @@
* for more details.
*/
+#ifndef __VIDEO_FBCON_H
+#define __VIDEO_FBCON_H
+
#include <linux/console_struct.h>
@@ -16,8 +19,7 @@
*/
struct display_switch {
- int (*open)(struct display *p);
- void (*release)(void);
+ void (*setup)(struct display *p);
void (*bmove)(struct display *p, int sy, int sx, int dy, int dx,
int height, int width);
void (*clear)(struct vc_data *conp, struct display *p, int sy, int sx,
@@ -26,20 +28,11 @@ struct display_switch {
int xx);
void (*putcs)(struct vc_data *conp, struct display *p, const char *s,
int count, int yy, int xx);
- void (*rev_char)(struct display *p, int xx, int yy);
- struct display_switch *next;
+ void (*revc)(struct display *p, int xx, int yy);
};
/*
- * Driver registration
- */
-
-extern int fbcon_register_driver(struct display_switch *dispsw, int is_accel);
-int fbcon_unregister_driver(struct display_switch *dispsw);
-
-
- /*
* Attribute Decoding
*/
@@ -335,3 +328,5 @@ static __inline__ void fast_memmove(char *dst, const char *src, size_t size)
}
#endif /* !m68k */
+
+#endif /* __VIDEO_FBCON_H */
diff --git a/drivers/video/fbgen.c b/drivers/video/fbgen.c
new file mode 100644
index 000000000..730438d16
--- /dev/null
+++ b/drivers/video/fbgen.c
@@ -0,0 +1,386 @@
+/*
+ * linux/drivers/video/fbgen.c -- Generic routines for frame buffer devices
+ *
+ * Created 3 Jan 1998 by Geert Uytterhoeven
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file README.legal in the main directory of this archive
+ * for more details.
+ */
+
+#include <linux/module.h>
+#include <linux/string.h>
+#include <linux/tty.h>
+#include <linux/fb.h>
+#include <linux/slab.h>
+
+#include <asm/uaccess.h>
+
+
+
+static int currcon = 0;
+
+static struct display disp;
+
+
+ /*
+ * `Generic' versions of the frame buffer device operations
+ */
+
+extern int fbgen_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+extern int fbgen_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+extern int fbgen_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+extern int fbgen_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+extern int fbgen_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+extern int fbgen_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+extern int fbgen_ioctl(struct inode *inode, struct file *file,
+ unsigned int cmd, unsigned long arg, int con,
+ struct fb_info *info);
+
+
+ /*
+ * Helper functions
+ */
+
+int fbgen_do_set_var(struct fb_var_screeninfo *var, int isactive,
+ struct fb_info_gen *info);
+void fbgen_set_disp(int con, struct fb_info_gen *info);
+void fbgen_install_cmap(int con, struct fb_info_gen *info);
+int fbgen_update_var(int con, struct fb_info *info);
+int fbgen_switch(int con, struct fb_info *info);
+void fbgen_blank(int blank, struct fb_info *info);
+
+
+/* ---- `Generic' versions of the frame buffer device operations ----------- */
+
+
+ /*
+ * Get the Fixed Part of the Display
+ */
+
+int fbgen_get_fix(struct fb_fix_screeninfo *fix, int con, struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+ char par[info2->parsize];
+
+ if (con == -1)
+ fbhw->get_par(&par, info2);
+ else {
+ int err;
+
+ if ((err = fbhw->decode_var(&fb_display[con].var, &par, info2)))
+ return err;
+ }
+ memset(fix, 0, sizeof(struct fb_fix_screeninfo));
+ return fbhw->encode_fix(fix, &par, info2);
+}
+
+
+ /*
+ * Get the User Defined Part of the Display
+ */
+
+int fbgen_get_var(struct fb_var_screeninfo *var, int con, struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+ char par[info2->parsize];
+
+ if (con == -1) {
+ fbhw->get_par(&par, info2);
+ fbhw->encode_var(var, &par, info2);
+ } else
+ *var = fb_display[con].var;
+ return 0;
+}
+
+
+ /*
+ * Set the User Defined Part of the Display
+ */
+
+int fbgen_set_var(struct fb_var_screeninfo *var, int con, struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ int err;
+ int oldxres, oldyres, oldbpp, oldxres_virtual, oldyres_virtual, oldyoffset;
+
+ if ((err = fbgen_do_set_var(var, con == currcon, info2)))
+ return err;
+ if ((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) {
+ oldxres = fb_display[con].var.xres;
+ oldyres = fb_display[con].var.yres;
+ oldxres_virtual = fb_display[con].var.xres_virtual;
+ oldyres_virtual = fb_display[con].var.yres_virtual;
+ oldbpp = fb_display[con].var.bits_per_pixel;
+ oldyoffset = fb_display[con].var.yoffset;
+ fb_display[con].var = *var;
+ if (oldxres != var->xres || oldyres != var->yres ||
+ oldxres_virtual != var->xres_virtual ||
+ oldyres_virtual != var->yres_virtual ||
+ oldbpp != var->bits_per_pixel ||
+ oldyoffset != var->yoffset) {
+ fbgen_set_disp(con, info2);
+ if (info->changevar)
+ (*info->changevar)(con);
+ if ((err = fb_alloc_cmap(&fb_display[con].cmap, 0, 0)))
+ return err;
+ fbgen_install_cmap(con, info2);
+ }
+ }
+ var->activate = 0;
+ return 0;
+}
+
+
+ /*
+ * Get the Colormap
+ */
+
+int fbgen_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+
+ if (con == currcon) /* current console ? */
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, fbhw->getcolreg,
+ info);
+ else
+ if (fb_display[con].cmap.len) /* non default colormap ? */
+ fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
+ else
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ cmap, kspc ? 0 : 2);
+ return 0;
+}
+
+
+ /*
+ * Set the Colormap
+ */
+
+int fbgen_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+ int err;
+
+ if (!fb_display[con].cmap.len) { /* no colormap allocated ? */
+ if ((err = fb_alloc_cmap(&fb_display[con].cmap,
+ 1 << fb_display[con].var.bits_per_pixel, 0)))
+ return err;
+ }
+ if (con == currcon) /* current console ? */
+ return fb_set_cmap(cmap, &fb_display[con].var, kspc, fbhw->setcolreg,
+ info);
+ else
+ fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
+ return 0;
+}
+
+
+ /*
+ * Pan or Wrap the Display
+ *
+ * This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
+ */
+
+int fbgen_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+ int xoffset = var->xoffset;
+ int yoffset = var->yoffset;
+ int err;
+
+ if (xoffset < 0 ||
+ xoffset+fb_display[con].var.xres > fb_display[con].var.xres_virtual ||
+ yoffset < 0 ||
+ yoffset+fb_display[con].var.yres > fb_display[con].var.yres_virtual)
+ return -EINVAL;
+ if (con == currcon) {
+ if (fbhw->pan_display) {
+ if ((err = fbhw->pan_display(var, info2)))
+ return err;
+ } else
+ return -EINVAL;
+ }
+ fb_display[con].var.xoffset = var->xoffset;
+ fb_display[con].var.yoffset = var->yoffset;
+ if (var->vmode & FB_VMODE_YWRAP)
+ fb_display[con].var.vmode |= FB_VMODE_YWRAP;
+ else
+ fb_display[con].var.vmode &= ~FB_VMODE_YWRAP;
+
+ return 0;
+}
+
+
+ /*
+ * Frame Buffer Specific ioctls
+ */
+
+int fbgen_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
+ unsigned long arg, int con, struct fb_info *info)
+{
+ return -EINVAL;
+}
+
+
+/* ---- Helper functions --------------------------------------------------- */
+
+
+ /*
+ * Change the video mode
+ */
+
+int fbgen_do_set_var(struct fb_var_screeninfo *var, int isactive,
+ struct fb_info_gen *info)
+{
+ struct fbgen_hwswitch *fbhw = info->fbhw;
+ int err, activate;
+ char par[info->parsize];
+
+ if ((err = fbhw->decode_var(var, &par, info)))
+ return err;
+ activate = var->activate;
+ if (((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) && isactive)
+ fbhw->set_par(&par, info);
+ fbhw->encode_var(var, &par, info);
+ var->activate = activate;
+ return 0;
+}
+
+
+void fbgen_set_disp(int con, struct fb_info_gen *info)
+{
+ struct fbgen_hwswitch *fbhw = info->fbhw;
+ struct fb_fix_screeninfo fix;
+ char par[info->parsize];
+ struct display *display;
+
+ if (con >= 0)
+ display = &fb_display[con];
+ else
+ display = &disp; /* used during initialization */
+
+ if (con == -1)
+ fbhw->get_par(&par, info);
+ else
+ fbhw->decode_var(&fb_display[con].var, &par, info);
+ memset(&fix, 0, sizeof(struct fb_fix_screeninfo));
+ fbhw->encode_fix(&fix, &par, info);
+
+ display->screen_base = fix.smem_start;
+ display->visual = fix.visual;
+ display->type = fix.type;
+ display->type_aux = fix.type_aux;
+ display->ypanstep = fix.ypanstep;
+ display->ywrapstep = fix.ywrapstep;
+ display->line_length = fix.line_length;
+ if (info->fbhw->blank || fix.visual == FB_VISUAL_PSEUDOCOLOR ||
+ fix.visual == FB_VISUAL_DIRECTCOLOR)
+ display->can_soft_blank = 1;
+ else
+ display->can_soft_blank = 0;
+ display->dispsw = fbhw->get_dispsw(&par, info);
+#if 0 /* FIXME: generic inverse is not supported yet */
+ display->inverse = (fix.visual == FB_VISUAL_MONO01 ? !inverse : inverse);
+#else
+ display->inverse = fix.visual == FB_VISUAL_MONO01;
+#endif
+}
+
+
+ /*
+ * Install the current colormap
+ */
+
+void fbgen_install_cmap(int con, struct fb_info_gen *info)
+{
+ struct fbgen_hwswitch *fbhw = info->fbhw;
+ if (con != currcon)
+ return;
+ if (fb_display[con].cmap.len)
+ fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
+ fbhw->setcolreg, &info->info);
+ else
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, fbhw->setcolreg, &info->info);
+}
+
+
+ /*
+ * Update the `var' structure (called by fbcon.c)
+ */
+
+int fbgen_update_var(int con, struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+ int err;
+
+ if (fbhw->pan_display) {
+ if ((err = fbhw->pan_display(&fb_display[con].var, info2)))
+ return err;
+ }
+ return 0;
+}
+
+
+ /*
+ * Switch to a different virtual console
+ */
+
+int fbgen_switch(int con, struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+
+ /* Do we have to save the colormap ? */
+ if (fb_display[currcon].cmap.len)
+ fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
+ fbhw->getcolreg, &info2->info);
+ fbgen_do_set_var(&fb_display[con].var, 1, info2);
+ currcon = con;
+ /* Install new colormap */
+ fbgen_install_cmap(con, info2);
+ return 0;
+}
+
+
+ /*
+ * Blank the screen
+ */
+
+void fbgen_blank(int blank, struct fb_info *info)
+{
+ struct fb_info_gen *info2 = (struct fb_info_gen *)info;
+ struct fbgen_hwswitch *fbhw = info2->fbhw;
+ u16 black[16];
+ struct fb_cmap cmap;
+
+ if (fbhw->blank && !fbhw->blank(blank, info2))
+ return;
+ if (blank) {
+ memset(black, 0, 16*sizeof(u16));
+ cmap.red = black;
+ cmap.green = black;
+ cmap.blue = black;
+ cmap.transp = NULL;
+ cmap.start = 0;
+ cmap.len = 16;
+ fb_set_cmap(&cmap, &fb_display[currcon].var, 1, fbhw->setcolreg, info);
+ } else
+ fbgen_install_cmap(currcon, info2);
+}
diff --git a/drivers/video/font_6x11.c b/drivers/video/font_6x11.c
new file mode 100644
index 000000000..ebfe24258
--- /dev/null
+++ b/drivers/video/font_6x11.c
@@ -0,0 +1,3345 @@
+/**********************************************/
+/* */
+/* Font file generated by rthelen */
+/* */
+/**********************************************/
+
+#define FONTDATAMAX (11*256)
+
+char fontname_6x11[] = "ProFont6x11";
+
+int fontheight_6x11 = 11;
+int fontwidth_6x11 = 6;
+
+unsigned char fontdata_6x11[FONTDATAMAX] = {
+
+ /* 0 0x00 '^A' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 1 0x01 '^B' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 2 0x02 '^C' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 3 0x03 '^D' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 4 0x04 '^E' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 5 0x05 '^F' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 6 0x06 '^G' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 7 0x07 '^H' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 8 0x08 '^I' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 9 0x09 '^J' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 10 0x0a '^K' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 11 0x0b '^L' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 12 0x0c '^M' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 13 0x0d '^N' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 14 0x0e '^O' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 15 0x0f '^P' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 16 0x10 '^Q' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 17 0x11 '^R' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x38, /* 00 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 18 0x12 '^S' */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x50, /* 0 0 0000 */
+ 0x50, /* 0 0 0000 */
+ 0x20, /* 00 00000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 19 0x13 '^T' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x7c, /* 0 00 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 20 0x14 '^U' */
+ 0x18, /* 000 000 */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x7c, /* 0 00 */
+ 0x78, /* 0 000 */
+ 0x78, /* 0 000 */
+ 0x7c, /* 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 21 0x15 '^V' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 22 0x16 '^W' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 23 0x17 '^X' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 24 0x18 '^Y' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 25 0x19 '^Z' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 26 0x1a '^[' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 27 0x1b '^\' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 28 0x1c '^]' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 29 0x1d '^^' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 30 0x1e '^_' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 31 0x1f '^`' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 32 0x20 ' ' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 33 0x21 '!' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 34 0x22 '"' */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 35 0x23 '#' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x7c, /* 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x7c, /* 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 36 0x24 '$' */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x50, /* 0 0 0000 */
+ 0x38, /* 00 000 */
+ 0x14, /* 000 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 37 0x25 '%' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x58, /* 0 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x34, /* 00 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x48, /* 0 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 38 0x26 '&' */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x48, /* 0 00 000 */
+ 0x50, /* 0 0 0000 */
+ 0x20, /* 00 00000 */
+ 0x54, /* 0 0 0 00 */
+ 0x48, /* 0 00 000 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 39 0x27 ''' */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 40 0x28 '(' */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x04, /* 00000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 41 0x29 ')' */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 42 0x2a '*' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x54, /* 0 0 0 00 */
+ 0x38, /* 00 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 43 0x2b '+' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x7c, /* 0 00 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 44 0x2c ',' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x30, /* 00 0000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+
+ /* 45 0x2d '-' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 46 0x2e '.' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x18, /* 000 000 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 47 0x2f '/' */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x20, /* 00 00000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+
+ /* 48 0x30 '0' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x64, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 49 0x31 '1' */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x18, /* 000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x1c, /* 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 50 0x32 '2' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 51 0x33 '3' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x04, /* 00000 00 */
+ 0x18, /* 000 000 */
+ 0x04, /* 00000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 52 0x34 '4' */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x18, /* 000 000 */
+ 0x28, /* 00 0 000 */
+ 0x48, /* 0 00 000 */
+ 0x7c, /* 0 00 */
+ 0x08, /* 0000 000 */
+ 0x1c, /* 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 53 0x35 '5' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 54 0x36 '6' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 55 0x37 '7' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 56 0x38 '8' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 57 0x39 '9' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x3c, /* 00 00 */
+ 0x04, /* 00000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 58 0x3a ':' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x18, /* 000 000 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x18, /* 000 000 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 59 0x3b ';' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x30, /* 00 0000 */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x30, /* 00 0000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+
+ /* 60 0x3c '<' */
+ 0x00, /* 00000000 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x04, /* 00000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 61 0x3d '=' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 62 0x3e '>' */
+ 0x00, /* 00000000 */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 63 0x3f '?' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 64 0x40 '@' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x74, /* 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x78, /* 0 000 */
+ 0x40, /* 0 000000 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 65 0x41 'A' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 66 0x42 'B' */
+ 0x00, /* 00000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 67 0x43 'C' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 68 0x44 'D' */
+ 0x00, /* 00000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 69 0x45 'E' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 70 0x46 'F' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 71 0x47 'G' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x40, /* 0 000000 */
+ 0x4c, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 72 0x48 'H' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 73 0x49 'I' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 74 0x4a 'J' */
+ 0x00, /* 00000000 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 75 0x4b 'K' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x48, /* 0 00 000 */
+ 0x50, /* 0 0 0000 */
+ 0x60, /* 0 00000 */
+ 0x50, /* 0 0 0000 */
+ 0x48, /* 0 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 76 0x4c 'L' */
+ 0x00, /* 00000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 77 0x4d 'M' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x6c, /* 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 78 0x4e 'N' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x64, /* 0 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x4c, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 79 0x4f 'O' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 80 0x50 'P' */
+ 0x00, /* 00000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 81 0x51 'Q' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x38, /* 00 000 */
+ 0x04, /* 00000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 82 0x52 'R' */
+ 0x00, /* 00000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 83 0x53 'S' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x40, /* 0 000000 */
+ 0x38, /* 00 000 */
+ 0x04, /* 00000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 84 0x54 'T' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 85 0x55 'U' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 86 0x56 'V' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 87 0x57 'W' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x6c, /* 0 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 88 0x58 'X' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 89 0x59 'Y' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 90 0x5a 'Z' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x40, /* 0 000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 91 0x5b '[' */
+ 0x0c, /* 0000 00 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x0c, /* 0000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 92 0x5c '\' */
+ 0x20, /* 00 00000 */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x02, /* 000000 0 */
+ 0x02, /* 000000 0 */
+ 0x00, /* 00000000 */
+
+ /* 93 0x5d ']' */
+ 0x30, /* 00 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x30, /* 00 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 94 0x5e '^' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 95 0x5f '_' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7e, /* 0 0 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 96 0x60 '`' */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 97 0x61 'a' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 98 0x62 'b' */
+ 0x00, /* 00000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 99 0x63 'c' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x40, /* 0 000000 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 100 0x64 'd' */
+ 0x00, /* 00000000 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 101 0x65 'e' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 102 0x66 'f' */
+ 0x00, /* 00000000 */
+ 0x0c, /* 0000 00 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 103 0x67 'g' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x3c, /* 00 00 */
+ 0x04, /* 00000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+
+ /* 104 0x68 'h' */
+ 0x00, /* 00000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 105 0x69 'i' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 106 0x6a 'j' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x60, /* 0 00000 */
+ 0x00, /* 00000000 */
+
+ /* 107 0x6b 'k' */
+ 0x00, /* 00000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x48, /* 0 00 000 */
+ 0x50, /* 0 0 0000 */
+ 0x70, /* 0 0000 */
+ 0x48, /* 0 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 108 0x6c 'l' */
+ 0x00, /* 00000000 */
+ 0x30, /* 00 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 109 0x6d 'm' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x78, /* 0 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 110 0x6e 'n' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x58, /* 0 0 000 */
+ 0x64, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 111 0x6f 'o' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 112 0x70 'p' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x78, /* 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+
+ /* 113 0x71 'q' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x3c, /* 00 00 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x00, /* 00000000 */
+
+ /* 114 0x72 'r' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x58, /* 0 0 000 */
+ 0x64, /* 0 00 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 115 0x73 's' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x40, /* 0 000000 */
+ 0x38, /* 00 000 */
+ 0x04, /* 00000 00 */
+ 0x78, /* 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 116 0x74 't' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x0c, /* 0000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 117 0x75 'u' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 118 0x76 'v' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 119 0x77 'w' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 120 0x78 'x' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 121 0x79 'y' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x3c, /* 00 00 */
+ 0x04, /* 00000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+
+ /* 122 0x7a 'z' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 123 0x7b '{' */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x04, /* 00000 00 */
+ 0x00, /* 00000000 */
+
+ /* 124 0x7c '|' */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 125 0x7d '}' */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+
+ /* 126 0x7e '~' */
+ 0x00, /* 00000000 */
+ 0x34, /* 00 0 00 */
+ 0x58, /* 0 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 127 0x7f '^?' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 128 0x80 '\200' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 129 0x81 '\201' */
+ 0x28, /* 00 0 000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 130 0x82 '\202' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 131 0x83 '\203' */
+ 0x10, /* 000 0000 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x78, /* 0 000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 132 0x84 '\204' */
+ 0x58, /* 0 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x64, /* 0 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x4c, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 133 0x85 '\205' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 134 0x86 '\206' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 135 0x87 '\207' */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 136 0x88 '\210' */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 137 0x89 '\211' */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 138 0x8a '\212' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 139 0x8b '\213' */
+ 0x34, /* 00 0 00 */
+ 0x58, /* 0 0 000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 140 0x8c '\214' */
+ 0x18, /* 000 000 */
+ 0x24, /* 00 00 00 */
+ 0x18, /* 000 000 */
+ 0x3c, /* 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 141 0x8d '\215' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x3c, /* 00 00 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+
+ /* 142 0x8e '\216' */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 143 0x8f '\217' */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 144 0x90 '\220' */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 145 0x91 '\221' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x40, /* 0 000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 146 0x92 '\222' */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 147 0x93 '\223' */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 148 0x94 '\224' */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 149 0x95 '\225' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 150 0x96 '\226' */
+ 0x34, /* 00 0 00 */
+ 0x58, /* 0 0 000 */
+ 0x00, /* 00000000 */
+ 0x58, /* 0 0 000 */
+ 0x64, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 151 0x97 '\227' */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 152 0x98 '\230' */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 153 0x99 '\231' */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 154 0x9a '\232' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 155 0x9b '\233' */
+ 0x34, /* 00 0 00 */
+ 0x58, /* 0 0 000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 156 0x9c '\234' */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 157 0x9d '\235' */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 158 0x9e '\236' */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 159 0x9f '\237' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x34, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 160 0xa0 '\240' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 161 0xa1 '\241' */
+ 0x18, /* 000 000 */
+ 0x24, /* 00 00 00 */
+ 0x24, /* 00 00 00 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 162 0xa2 '\242' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x50, /* 0 0 0000 */
+ 0x54, /* 0 0 0 00 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 163 0xa3 '\243' */
+ 0x30, /* 00 0000 */
+ 0x48, /* 0 00 000 */
+ 0x40, /* 0 000000 */
+ 0x70, /* 0 0000 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x44, /* 0 000 00 */
+ 0x78, /* 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 164 0xa4 '\244' */
+ 0x44, /* 0 000 00 */
+ 0x24, /* 00 00 00 */
+ 0x50, /* 0 0 0000 */
+ 0x48, /* 0 00 000 */
+ 0x24, /* 00 00 00 */
+ 0x14, /* 000 0 00 */
+ 0x48, /* 0 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 165 0xa5 '\245' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x7c, /* 0 00 */
+ 0x7c, /* 0 00 */
+ 0x7c, /* 0 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 166 0xa6 '\246' */
+ 0x3c, /* 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x3c, /* 00 00 */
+ 0x14, /* 000 0 00 */
+ 0x14, /* 000 0 00 */
+ 0x14, /* 000 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 167 0xa7 '\247' */
+ 0x18, /* 000 000 */
+ 0x24, /* 00 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x48, /* 0 00 000 */
+ 0x48, /* 0 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x58, /* 0 0 000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 168 0xa8 '\250' */
+ 0x00, /* 00000000 */
+ 0x70, /* 0 0000 */
+ 0x08, /* 0000 000 */
+ 0x64, /* 0 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x64, /* 0 00 00 */
+ 0x58, /* 0 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 169 0xa9 '\251' */
+ 0x00, /* 00000000 */
+ 0x70, /* 0 0000 */
+ 0x08, /* 0000 000 */
+ 0x34, /* 00 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x34, /* 00 0 00 */
+ 0x08, /* 0000 000 */
+ 0x70, /* 0 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 170 0xaa '\252' */
+ 0x00, /* 00000000 */
+ 0x7a, /* 0 0 0 */
+ 0x2e, /* 00 0 0 */
+ 0x2e, /* 00 0 0 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 171 0xab '\253' */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 172 0xac '\254' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 173 0xad '\255' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x7c, /* 0 00 */
+ 0x10, /* 000 0000 */
+ 0x7c, /* 0 00 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 174 0xae '\256' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x50, /* 0 0 0000 */
+ 0x50, /* 0 0 0000 */
+ 0x78, /* 0 000 */
+ 0x50, /* 0 0 0000 */
+ 0x50, /* 0 0 0000 */
+ 0x5c, /* 0 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 175 0xaf '\257' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x4c, /* 0 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x64, /* 0 00 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 176 0xb0 '\260' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x6c, /* 0 0 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x6c, /* 0 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 177 0xb1 '\261' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x7c, /* 0 00 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 178 0xb2 '\262' */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 179 0xb3 '\263' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x04, /* 00000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x1c, /* 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 180 0xb4 '\264' */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x7c, /* 0 00 */
+ 0x10, /* 000 0000 */
+ 0x7c, /* 0 00 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 181 0xb5 '\265' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x48, /* 0 00 000 */
+ 0x48, /* 0 00 000 */
+ 0x48, /* 0 00 000 */
+ 0x48, /* 0 00 000 */
+ 0x74, /* 0 0 00 */
+ 0x40, /* 0 000000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+
+ /* 182 0xb6 '\266' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x0c, /* 0000 00 */
+ 0x14, /* 000 0 00 */
+ 0x24, /* 00 00 00 */
+ 0x24, /* 00 00 00 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 183 0xb7 '\267' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x24, /* 00 00 00 */
+ 0x10, /* 000 0000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x24, /* 00 00 00 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 184 0xb8 '\270' */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 185 0xb9 '\271' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 186 0xba '\272' */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x60, /* 0 00000 */
+ 0x00, /* 00000000 */
+
+ /* 187 0xbb '\273' */
+ 0x00, /* 00000000 */
+ 0x1c, /* 000 00 */
+ 0x24, /* 00 00 00 */
+ 0x24, /* 00 00 00 */
+ 0x1c, /* 000 00 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 188 0xbc '\274' */
+ 0x00, /* 00000000 */
+ 0x18, /* 000 000 */
+ 0x24, /* 00 00 00 */
+ 0x24, /* 00 00 00 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 189 0xbd '\275' */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x6c, /* 0 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 190 0xbe '\276' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x5c, /* 0 0 00 */
+ 0x50, /* 0 0 0000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 191 0xbf '\277' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x4c, /* 0 00 00 */
+ 0x54, /* 0 0 0 00 */
+ 0x64, /* 0 00 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 192 0xc0 '\300' */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x20, /* 00 00000 */
+ 0x40, /* 0 000000 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 193 0xc1 '\301' */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x08, /* 0000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 194 0xc2 '\302' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x04, /* 00000 00 */
+ 0x04, /* 00000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 195 0xc3 '\303' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x0c, /* 0000 00 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x50, /* 0 0 0000 */
+ 0x20, /* 00 00000 */
+ 0x20, /* 00 00000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 196 0xc4 '\304' */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x60, /* 0 00000 */
+ 0x00, /* 00000000 */
+
+ /* 197 0xc5 '\305' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x04, /* 00000 00 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x40, /* 0 000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 198 0xc6 '\306' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 199 0xc7 '\307' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x24, /* 00 00 00 */
+ 0x48, /* 0 00 000 */
+ 0x48, /* 0 00 000 */
+ 0x24, /* 00 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 200 0xc8 '\310' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x48, /* 0 00 000 */
+ 0x24, /* 00 00 00 */
+ 0x24, /* 00 00 00 */
+ 0x48, /* 0 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 201 0xc9 '\311' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x54, /* 0 0 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 202 0xca '\312' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 203 0xcb '\313' */
+ 0x10, /* 000 0000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 204 0xcc '\314' */
+ 0x58, /* 0 0 000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x7c, /* 0 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 205 0xcd '\315' */
+ 0x58, /* 0 0 000 */
+ 0x38, /* 00 000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 206 0xce '\316' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x50, /* 0 0 0000 */
+ 0x50, /* 0 0 0000 */
+ 0x58, /* 0 0 000 */
+ 0x50, /* 0 0 0000 */
+ 0x50, /* 0 0 0000 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 207 0xcf '\317' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x54, /* 0 0 0 00 */
+ 0x5c, /* 0 0 00 */
+ 0x50, /* 0 0 0000 */
+ 0x2c, /* 00 0 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 208 0xd0 '\320' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 209 0xd1 '\321' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7e, /* 0 0 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 210 0xd2 '\322' */
+ 0x00, /* 00000000 */
+ 0x14, /* 000 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 211 0xd3 '\323' */
+ 0x00, /* 00000000 */
+ 0x14, /* 000 0 00 */
+ 0x14, /* 000 0 00 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 212 0xd4 '\324' */
+ 0x00, /* 00000000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x18, /* 000 000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 213 0xd5 '\325' */
+ 0x00, /* 00000000 */
+ 0x18, /* 000 000 */
+ 0x08, /* 0000 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 214 0xd6 '\326' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x7c, /* 0 00 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 215 0xd7 '\327' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x10, /* 000 0000 */
+ 0x28, /* 00 0 000 */
+ 0x44, /* 0 000 00 */
+ 0x28, /* 00 0 000 */
+ 0x10, /* 000 0000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 216 0xd8 '\330' */
+ 0x00, /* 00000000 */
+ 0x28, /* 00 0 000 */
+ 0x00, /* 00000000 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x44, /* 0 000 00 */
+ 0x3c, /* 00 00 */
+ 0x04, /* 00000 00 */
+ 0x38, /* 00 000 */
+ 0x00, /* 00000000 */
+
+ /* 217 0xd9 '\331' */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x7e, /* 0 0 */
+ 0x00, /* 00000000 */
+ 0x7e, /* 0 0 */
+ 0x00, /* 00000000 */
+ 0x7e, /* 0 0 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 218 0xda '\332' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 219 0xdb '\333' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 220 0xdc '\334' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 221 0xdd '\335' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 222 0xde '\336' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 223 0xdf '\337' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 224 0xe0 '\340' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 225 0xe1 '\341' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 226 0xe2 '\342' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 227 0xe3 '\343' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 228 0xe4 '\344' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 229 0xe5 '\345' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 230 0xe6 '\346' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 231 0xe7 '\347' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 232 0xe8 '\350' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 233 0xe9 '\351' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 234 0xea '\352' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 235 0xeb '\353' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 236 0xec '\354' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 237 0xed '\355' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 238 0xee '\356' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 239 0xef '\357' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 240 0xf0 '\360' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 241 0xf1 '\361' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 242 0xf2 '\362' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 243 0xf3 '\363' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 244 0xf4 '\364' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 245 0xf5 '\365' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 246 0xf6 '\366' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 247 0xf7 '\367' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 248 0xf8 '\370' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 249 0xf9 '\371' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 250 0xfa '\372' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 251 0xfb '\373' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 252 0xfc '\374' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 253 0xfd '\375' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 254 0xfe '\376' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+ /* 255 0xff '\377' */
+ 0x00, /* 00000000 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x3c, /* 00 00 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+ 0x00, /* 00000000 */
+
+};
+
diff --git a/drivers/video/fonts.c b/drivers/video/fonts.c
index 8e89805bb..56a3a33b2 100644
--- a/drivers/video/fonts.c
+++ b/drivers/video/fonts.c
@@ -9,7 +9,7 @@
*/
-#include <linux/config.h> /* for CONFIG_AMIGA */
+#include <linux/config.h>
#include <linux/types.h>
#include <linux/string.h>
#ifdef __mc68000__
@@ -25,17 +25,22 @@
/* VGA8x8 */
extern char fontname_8x8[];
extern int fontwidth_8x8, fontheight_8x8;
-extern u_char fontdata_8x8[];
+extern u8 fontdata_8x8[];
/* VGA8x16 */
extern char fontname_8x16[];
extern int fontwidth_8x16, fontheight_8x16;
-extern u_char fontdata_8x16[];
+extern u8 fontdata_8x16[];
/* PEARL8x8 */
extern char fontname_pearl8x8[];
extern int fontwidth_pearl8x8, fontheight_pearl8x8;
-extern u_char fontdata_pearl8x8[];
+extern u8 fontdata_pearl8x8[];
+
+/* VGA6x11 */
+extern char fontname_6x11[];
+extern int fontwidth_6x11, fontheight_6x11;
+extern u8 fontdata_6x11[];
/*
@@ -46,18 +51,20 @@ struct softfontdesc {
char *name;
int *width;
int *height;
- u_char *data;
+ u8 *data;
};
#define VGA8x8_IDX 0
#define VGA8x16_IDX 1
#define PEARL8x8_IDX 2
+#define VGA6x11_IDX 3
static struct softfontdesc softfonts[] = {
{ fontname_8x8, &fontwidth_8x8, &fontheight_8x8, fontdata_8x8 },
{ fontname_8x16, &fontwidth_8x16, &fontheight_8x16, fontdata_8x16 },
{ fontname_pearl8x8, &fontwidth_pearl8x8, &fontheight_pearl8x8,
fontdata_pearl8x8 },
+ { fontname_6x11, &fontwidth_6x11, &fontheight_6x11, fontdata_6x11 },
};
static unsigned int numsoftfonts = sizeof(softfonts)/sizeof(*softfonts);
@@ -67,7 +74,7 @@ static unsigned int numsoftfonts = sizeof(softfonts)/sizeof(*softfonts);
* Find a font with a specific name
*/
-int findsoftfont(char *name, int *width, int *height, u_char *data[])
+int findsoftfont(char *name, int *width, int *height, u8 *data[])
{
unsigned int i;
@@ -90,7 +97,7 @@ int findsoftfont(char *name, int *width, int *height, u_char *data[])
*/
void getdefaultfont(int xres, int yres, char *name[], int *width, int *height,
- u_char *data[])
+ u8 *data[])
{
int i;
@@ -103,6 +110,16 @@ void getdefaultfont(int xres, int yres, char *name[], int *width, int *height,
} else
i = VGA8x16_IDX;
+#if defined(CONFIG_MAC)
+ if (MACH_IS_MAC) {
+#if 0 /* MSch: removed until 6x11 is debugged */
+ i = VGA6x11_IDX; /* I added this for fun ... I like 6x11 */
+#endif
+ if (xres < 640)
+ i = VGA6x11_IDX;
+ }
+#endif
+
if (name)
*name = softfonts[i].name;
if (width)
diff --git a/drivers/video/macfb.c b/drivers/video/macfb.c
new file mode 100644
index 000000000..43932a080
--- /dev/null
+++ b/drivers/video/macfb.c
@@ -0,0 +1,459 @@
+/*
+ * We've been given MAC frame buffer info by the booter. Now go set it up
+ */
+
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/mm.h>
+#include <linux/tty.h>
+#include <linux/malloc.h>
+#include <linux/delay.h>
+#include <linux/nubus.h>
+#include <linux/init.h>
+
+#include <asm/setup.h>
+#include <asm/bootinfo.h>
+#include <asm/uaccess.h>
+#include <asm/pgtable.h>
+#include <asm/irq.h>
+#include <asm/macintosh.h>
+#include <linux/fb.h>
+
+
+/* conditionalize these ?? */
+#include "fbcon-mfb.h"
+#include "fbcon-cfb2.h"
+#include "fbcon-cfb4.h"
+#include "fbcon-cfb8.h"
+
+#define arraysize(x) (sizeof(x)/sizeof(*(x)))
+
+static struct fb_var_screeninfo macfb_defined={
+ 0,0,0,0, /* W,H, W, H (virtual) load xres,xres_virtual*/
+ 0,0, /* virtual -> visible no offset */
+ 8, /* depth -> load bits_per_pixel */
+ 0, /* greyscale ? */
+ {0,0,0}, /* R */
+ {0,0,0}, /* G */
+ {0,0,0}, /* B */
+ {0,0,0}, /* transparency */
+ 0, /* standard pixel format */
+ FB_ACTIVATE_NOW,
+ 274,195, /* 14" monitor *Mikael Nykvist's anyway* */
+ FB_ACCEL_NONE, /* The only way to accelerate a mac is .. */
+ 0L,0L,0L,0L,0L,
+ 0L,0L,0, /* No sync info */
+ FB_VMODE_NONINTERLACED,
+ {0,0,0,0,0,0}
+};
+
+#define NUM_TOTAL_MODES 1
+#define NUM_PREDEF_MODES 1
+
+static struct display disp;
+static struct fb_info fb_info;
+
+static int inverse = 0;
+
+struct macfb_par
+{
+ void *unused;
+};
+
+static int currcon = 0;
+static int current_par_valid = 0;
+struct macfb_par current_par;
+
+static int mac_xres,mac_yres,mac_depth, mac_xbytes, mac_vxres;
+static unsigned long mac_videobase;
+static unsigned long mac_videosize;
+
+ /*
+ * Open/Release the frame buffer device
+ */
+
+static int macfb_open(struct fb_info *info)
+{
+ /*
+ * Nothing, only a usage count for the moment
+ */
+ MOD_INC_USE_COUNT;
+ return(0);
+}
+
+static int macfb_release(struct fb_info *info)
+{
+ MOD_DEC_USE_COUNT;
+ return(0);
+}
+
+static void macfb_encode_var(struct fb_var_screeninfo *var,
+ struct macfb_par *par)
+{
+ int i=0;
+ var->xres=mac_xres;
+ var->yres=mac_yres;
+ var->xres_virtual=mac_vxres;
+ var->yres_virtual=var->yres;
+ var->xoffset=0;
+ var->yoffset=0;
+ var->bits_per_pixel = mac_depth;
+ var->grayscale=0;
+ var->transp.offset=0;
+ var->transp.length=0;
+ var->transp.msb_right=0;
+ var->nonstd=0;
+ var->activate=0;
+ var->height= -1;
+ var->width= -1;
+ var->accel=0;
+ var->vmode=FB_VMODE_NONINTERLACED;
+ var->pixclock=0;
+ var->sync=0;
+ var->left_margin=0;
+ var->right_margin=0;
+ var->upper_margin=0;
+ var->lower_margin=0;
+ var->hsync_len=0;
+ var->vsync_len=0;
+ for(i=0;i<arraysize(var->reserved);i++)
+ var->reserved[i]=0;
+ return;
+}
+
+
+static void macfb_get_par(struct macfb_par *par)
+{
+ *par=current_par;
+}
+
+static void macfb_set_par(struct macfb_par *par)
+{
+ current_par_valid=1;
+}
+
+static int fb_update_var(int con, struct fb_info *info)
+{
+ return 0;
+}
+
+static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
+{
+ struct macfb_par par;
+
+ macfb_get_par(&par);
+ macfb_encode_var(var, &par);
+ return 0;
+}
+
+extern int console_loglevel;
+
+static void macfb_encode_fix(struct fb_fix_screeninfo *fix,
+ struct macfb_par *par)
+{
+ int i;
+
+ memset(fix, 0, sizeof(struct fb_fix_screeninfo));
+ strcpy(fix->id,"Macintosh");
+
+ /*
+ * X works, but screen wraps ...
+ */
+ fix->smem_start=(char *)(mac_videobase&PAGE_MASK);
+ fix->smem_offset=(mac_videobase&~PAGE_MASK);
+ fix->smem_len=PAGE_ALIGN(mac_videosize);
+ fix->type = FB_TYPE_PACKED_PIXELS;
+ fix->visual = FB_VISUAL_PSEUDOCOLOR;
+ fix->xpanstep=0;
+ fix->ypanstep=0;
+ fix->ywrapstep=0;
+ fix->line_length=mac_xbytes;
+ return;
+}
+
+static int macfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
+{
+ struct macfb_par par;
+ macfb_get_par(&par);
+ macfb_encode_fix(fix, &par);
+ return 0;
+}
+
+static int macfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ struct macfb_par par;
+ if(con==-1)
+ {
+ macfb_get_par(&par);
+ macfb_encode_var(var, &par);
+ }
+ else
+ *var=fb_display[con].var;
+ return 0;
+}
+
+static void macfb_set_disp(int con)
+{
+ struct fb_fix_screeninfo fix;
+ struct display *display;
+
+ if (con >= 0)
+ display = &fb_display[con];
+ else
+ display = &disp; /* used during initialization */
+
+ macfb_get_fix(&fix, con, 0);
+
+ display->screen_base = (u_char *)(fix.smem_start+fix.smem_offset);
+ display->visual = fix.visual;
+ display->type = fix.type;
+ display->type_aux = fix.type_aux;
+ display->ypanstep = fix.ypanstep;
+ display->ywrapstep = fix.ywrapstep;
+ display->line_length = fix.line_length;
+ display->next_line = fix.line_length;
+ display->can_soft_blank = 0;
+ display->inverse = inverse;
+
+ switch (mac_depth) {
+#ifdef CONFIG_FBCON_MFB
+ case 1:
+ display->dispsw = &fbcon_mfb;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB2
+ case 2:
+ display->dispsw = &fbcon_cfb2;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB4
+ case 4:
+ display->dispsw = &fbcon_cfb4;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_cfb8;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ break;
+ }
+}
+
+static int macfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ int err;
+
+ if ((err=do_fb_set_var(var, 1)))
+ return err;
+ return 0;
+}
+
+static int macfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+#if 0
+ printk("macfb_get_cmap: not supported!\n");
+ /* interferes with X11 */
+ if (console_loglevel < 7)
+ return -EINVAL;
+ if (con == currcon) /* current console? */
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, 0 /*offb_getcolreg*/, info);
+ else if (fb_display[con].cmap.len) /* non default colormap? */
+ fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
+ else
+ fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ cmap, kspc ? 0 : 2);
+#endif
+ return 0;
+
+}
+
+static int macfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+#if 0
+ printk("macfb_set_cmap: not supported!\n");
+ if (console_loglevel < 7)
+ return -EINVAL;
+ if (!fb_display[con].cmap.len) { /* no colormap allocated? */
+ if ((err = fb_alloc_cmap(&fb_display[con].cmap,
+ 1<<fb_display[con].var.bits_per_pixel, 0)))
+ return err;
+ }
+ if (con == currcon) /* current console? */
+ return fb_set_cmap(cmap, &fb_display[con].var, kspc, 1 /*offb_setcolreg*/, info);
+ else
+ fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
+#endif
+ return 0;
+}
+
+static int macfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ /* no panning */
+ printk("macfb_pan: not supported!\n");
+ return -EINVAL;
+}
+
+static int macfb_ioctl(struct inode *inode, struct file *file,
+ unsigned int cmd, unsigned long arg, int con,
+ struct fb_info *info)
+{
+ printk("macfb_ioctl: not supported!\n");
+ return -EINVAL;
+}
+
+static struct fb_ops macfb_ops = {
+ macfb_open,
+ macfb_release,
+ macfb_get_fix,
+ macfb_get_var,
+ macfb_set_var,
+ macfb_get_cmap,
+ macfb_set_cmap,
+ macfb_pan_display,
+ NULL,
+ macfb_ioctl
+};
+
+void macfb_setup(char *options, int *ints)
+{
+ char *this_opt;
+ int temp;
+
+ fb_info.fontname[0] = '\0';
+
+ if (!options || !*options)
+ return;
+
+ for(this_opt=strtok(options,","); this_opt; this_opt=strtok(NULL,",")) {
+ if (!*this_opt) continue;
+
+ if (! strcmp(this_opt, "inverse"))
+ inverse=1;
+ else if (!strncmp(this_opt, "font:", 5)) {
+ strcpy(fb_info.fontname, this_opt+5);
+ printk("macfb_setup: option %s\n", this_opt);
+ }
+ }
+}
+
+static int macfb_switch(int con, struct fb_info *info)
+{
+ do_fb_set_var(&fb_display[con].var,1);
+ currcon=con;
+ return 0;
+}
+
+/* 0 unblank, 1 blank, 2 no vsync, 3 no hsync, 4 off */
+
+static void macfb_blank(int blank, struct fb_info *info)
+{
+ /* Not supported */
+}
+
+/*
+ * Nubus call back. This will give us our board identity and also
+ * other useful info we need later
+ */
+
+static int nubus_video_card(struct nubus_device_specifier *ns, int slot, struct nubus_type *nt)
+{
+ if(nt->category==NUBUS_CAT_DISPLAY)
+ return 0;
+ /* Claim all video cards. We dont yet do driver specifics tho. */
+ return -ENODEV;
+}
+
+static struct nubus_device_specifier nb_video={
+ nubus_video_card,
+ NULL
+};
+
+__initfunc(unsigned long macfb_init(unsigned long mem_start))
+{
+ /* nubus_remap the video .. */
+ int err;
+
+ if (!MACH_IS_MAC)
+ return mem_start;
+
+ mac_xres=mac_bi_data.dimensions&0xFFFF;
+ mac_yres=(mac_bi_data.dimensions&0xFFFF0000)>>16;
+ mac_depth=mac_bi_data.videodepth;
+ mac_xbytes=mac_bi_data.videorow;
+ mac_vxres = (mac_xbytes/mac_depth)*8;
+ mac_videosize=mac_xbytes*mac_yres;
+ mac_videobase=mac_bi_data.videoaddr;
+
+ printk("macfb_init: xres %d yres %d bpp %d addr %x size %d \n",
+ mac_xres, mac_yres, mac_depth, mac_videobase, mac_videosize);
+
+ mac_debugging_penguin(4);
+
+ /*
+ * Fill in the available video resolution
+ */
+
+ macfb_defined.xres=mac_xres;
+ macfb_defined.yres=mac_yres;
+ macfb_defined.xres_virtual=mac_vxres;
+ macfb_defined.yres_virtual=mac_yres;
+ macfb_defined.bits_per_pixel=mac_depth;
+
+
+ /*
+ * Let there be consoles..
+ */
+ strcpy(fb_info.modename, "Macintosh Builtin ");
+ fb_info.changevar = NULL;
+ fb_info.node = -1;
+ fb_info.fbops = &macfb_ops;
+ fb_info.disp=&disp;
+ fb_info.switch_con=&macfb_switch;
+ fb_info.updatevar=&fb_update_var;
+ fb_info.blank=&macfb_blank;
+ do_fb_set_var(&macfb_defined,1);
+
+ err=register_framebuffer(&fb_info);
+ if(err<0)
+ {
+ mac_boom(6);
+ return NULL;
+ }
+
+ macfb_get_var(&disp.var, -1, &fb_info);
+ macfb_set_disp(-1);
+
+ /*
+ * Register the nubus hook
+ */
+
+ register_nubus_device(&nb_video);
+
+ printk("fb%d: %s frame buffer device using %ldK of video memory\n",
+ GET_FB_IDX(fb_info.node), fb_info.modename, mac_videosize>>10);
+
+ return mem_start;
+}
+
+#if 0
+/*
+ * These two auxiliary debug functions should go away ASAP. Only usage:
+ * before the console output is up (after head.S come some other crucial
+ * setup routines :-)
+ *
+ * Now in debug.c ...
+ */
+#endif
diff --git a/drivers/video/offb.c b/drivers/video/offb.c
index cc521899a..26ab95dfb 100644
--- a/drivers/video/offb.c
+++ b/drivers/video/offb.c
@@ -12,6 +12,7 @@
* more details.
*/
+#include <linux/config.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
@@ -23,53 +24,83 @@
#include <linux/delay.h>
#include <linux/interrupt.h>
#include <linux/fb.h>
+#include <linux/selection.h>
#include <linux/init.h>
+#ifdef CONFIG_FB_COMPAT_XPMAC
+#include <linux/vc_ioctl.h>
+#endif
#include <asm/io.h>
#include <asm/prom.h>
+#include "fbcon-cfb8.h"
-#define arraysize(x) (sizeof(x)/sizeof(*(x)))
static int currcon = 0;
-static struct display disp;
-static struct fb_info fb_info;
-static struct { u_char red, green, blue, pad; } palette[256];
-static char offb_name[16] = "OFfb ";
-static volatile unsigned char *unknown_cmap_adr = NULL;
-static volatile unsigned char *unknown_cmap_data = NULL;
+struct fb_info_offb {
+ struct fb_info info;
+ struct fb_fix_screeninfo fix;
+ struct fb_var_screeninfo var;
+ struct display disp;
+ struct { u_char red, green, blue, pad; } palette[256];
+ volatile unsigned char *cmap_adr;
+ volatile unsigned char *cmap_data;
+};
+
+static struct fb_info_offb fb_info[FB_MAX];
+
+#ifdef __powerpc__
+#define mach_eieio() eieio()
+#else
+#define mach_eieio() do {} while (0)
+#endif
-static struct fb_fix_screeninfo fb_fix = { 0, };
-static struct fb_var_screeninfo fb_var = { 0, };
+static int ofonly = 0;
/*
* Interface used by the world
*/
-void offb_video_setup(char *options, int *ints);
-
-static int offb_open(int fbidx);
-static int offb_release(int fbidx);
-static int offb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int offb_get_var(struct fb_var_screeninfo *var, int con);
-static int offb_set_var(struct fb_var_screeninfo *var, int con);
-static int offb_pan_display(struct fb_var_screeninfo *var, int con);
-static int offb_get_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int offb_set_cmap(struct fb_cmap *cmap, int kspc, int con);
+unsigned long offb_init(unsigned long mem_start);
+void offb_setup(char *options, int *ints);
+
+static int offb_open(struct fb_info *info);
+static int offb_release(struct fb_info *info);
+static int offb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int offb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int offb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int offb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int offb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int offb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
static int offb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con);
+ u_long arg, int con, struct fb_info *info);
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+int console_getmode(struct vc_mode *);
+int console_setmode(struct vc_mode *, int);
+int console_powermode(int);
+struct fb_info *console_fb_info = NULL;
+int (*console_setmode_ptr)(struct vc_mode *, int) = NULL;
+int (*console_set_cmap_ptr)(struct fb_cmap *, int, int, struct fb_info *)
+ = NULL;
+struct vc_mode display_info;
+#endif /* CONFIG_FB_COMPAT_XPMAC */
/*
* Interface to the low level console driver
*/
-unsigned long offb_init(unsigned long mem_start);
-static int offbcon_switch(int con);
-static int offbcon_updatevar(int con);
-static void offbcon_blank(int blank);
-static int offbcon_setcmap(struct fb_cmap *cmap, int con);
+static int offbcon_switch(int con, struct fb_info *info);
+static int offbcon_updatevar(int con, struct fb_info *info);
+static void offbcon_blank(int blank, struct fb_info *info);
/*
@@ -77,15 +108,15 @@ static int offbcon_setcmap(struct fb_cmap *cmap, int con);
*/
static int offb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp);
+ u_int *transp, struct fb_info *info);
static int offb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp);
-static void do_install_cmap(int con);
+ u_int transp, struct fb_info *info);
+static void do_install_cmap(int con, struct fb_info *info);
static struct fb_ops offb_ops = {
offb_open, offb_release, offb_get_fix, offb_get_var, offb_set_var,
- offb_get_cmap, offb_set_cmap, offb_pan_display, offb_ioctl
+ offb_get_cmap, offb_set_cmap, offb_pan_display, NULL, offb_ioctl
};
@@ -93,20 +124,20 @@ static struct fb_ops offb_ops = {
* Open/Release the frame buffer device
*/
-static int offb_open(int fbidx)
+static int offb_open(struct fb_info *info)
{
- /*
- * Nothing, only a usage count for the moment
- */
+ /*
+ * Nothing, only a usage count for the moment
+ */
MOD_INC_USE_COUNT;
- return(0);
+ return(0);
}
-
-static int offb_release(int fbidx)
+
+static int offb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
- return(0);
+ return(0);
}
@@ -114,9 +145,12 @@ static int offb_release(int fbidx)
* Get the Fixed Part of the Display
*/
-static int offb_get_fix(struct fb_fix_screeninfo *fix, int con)
+static int offb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
{
- memcpy(fix, &fb_fix, sizeof(fb_fix));
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
+
+ memcpy(fix, &info2->fix, sizeof(struct fb_fix_screeninfo));
return 0;
}
@@ -125,9 +159,12 @@ static int offb_get_fix(struct fb_fix_screeninfo *fix, int con)
* Get the User Defined Part of the Display
*/
-static int offb_get_var(struct fb_var_screeninfo *var, int con)
+static int offb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
- memcpy(var, &fb_var, sizeof(fb_var));
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
+
+ memcpy(var, &info2->var, sizeof(struct fb_var_screeninfo));
return 0;
}
@@ -136,33 +173,36 @@ static int offb_get_var(struct fb_var_screeninfo *var, int con)
* Set the User Defined Part of the Display
*/
-static int offb_set_var(struct fb_var_screeninfo *var, int con)
+static int offb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
struct display *display;
int oldbpp = -1, err;
+ int activate = var->activate;
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
if (con >= 0)
display = &fb_display[con];
else
- display = &disp; /* used during initialization */
+ display = &info2->disp; /* used during initialization */
- if (var->xres > fb_var.xres || var->yres > fb_var.yres ||
- var->xres_virtual > fb_var.xres_virtual ||
- var->yres_virtual > fb_var.yres_virtual ||
- var->bits_per_pixel > fb_var.bits_per_pixel ||
+ if (var->xres > info2->var.xres || var->yres > info2->var.yres ||
+ var->xres_virtual > info2->var.xres_virtual ||
+ var->yres_virtual > info2->var.yres_virtual ||
+ var->bits_per_pixel > info2->var.bits_per_pixel ||
var->nonstd ||
(var->vmode & FB_VMODE_MASK) != FB_VMODE_NONINTERLACED)
return -EINVAL;
- memcpy(var, &fb_var, sizeof(fb_var));
+ memcpy(var, &info2->var, sizeof(struct fb_var_screeninfo));
- if ((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) {
+ if ((activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) {
oldbpp = display->var.bits_per_pixel;
display->var = *var;
}
if (oldbpp != var->bits_per_pixel) {
if ((err = fb_alloc_cmap(&display->cmap, 0, 0)))
return err;
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
return 0;
}
@@ -174,7 +214,8 @@ static int offb_set_var(struct fb_var_screeninfo *var, int con)
* This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
*/
-static int offb_pan_display(struct fb_var_screeninfo *var, int con)
+static int offb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
if (var->xoffset || var->yoffset)
return -EINVAL;
@@ -186,14 +227,16 @@ static int offb_pan_display(struct fb_var_screeninfo *var, int con)
* Get the Colormap
*/
-static int offb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int offb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
if (con == currcon) /* current console? */
- return fb_get_cmap(cmap, &fb_display[con].var, kspc, offb_getcolreg);
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, offb_getcolreg,
+ info);
else if (fb_display[con].cmap.len) /* non default colormap? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return 0;
}
@@ -202,11 +245,13 @@ static int offb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
* Set the Colormap
*/
-static int offb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int offb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
int err;
- if (!unknown_cmap_adr)
+ if (!info2->cmap_adr)
return -ENOSYS;
if (!fb_display[con].cmap.len) { /* no colormap allocated? */
@@ -215,7 +260,8 @@ static int offb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
return err;
}
if (con == currcon) /* current console? */
- return fb_set_cmap(cmap, &fb_display[con].var, kspc, offb_setcolreg);
+ return fb_set_cmap(cmap, &fb_display[con].var, kspc, offb_setcolreg,
+ info);
else
fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
return 0;
@@ -223,12 +269,24 @@ static int offb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
static int offb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con)
+ u_long arg, int con, struct fb_info *info)
{
return -EINVAL;
}
+#ifdef CONFIG_FB_ATY
+extern unsigned long atyfb_of_init(unsigned long mem_start,
+ struct device_node *dp);
+
+static const char *aty_names[] = {
+ "ATY,mach64", "ATY,XCLAIM", "ATY,264VT", "ATY,mach64ii", "ATY,264GT-B",
+ "ATY,mach64_3D_pcc", "ATY,XCLAIM3D", "ATY,XCLAIMVR", "ATY,RAGEII_M",
+ "ATY,XCLAIMVRPro", "ATY,mach64_3DU"
+};
+#endif /* CONFIG_FB_ATY */
+
+
/*
* Initialisation
*/
@@ -236,128 +294,196 @@ static int offb_ioctl(struct inode *inode, struct file *file, u_int cmd,
__initfunc(unsigned long offb_init(unsigned long mem_start))
{
struct device_node *dp;
- int i, err, *pp, len;
+ int dpy, i, err, *pp, len;
unsigned *up, address;
+ struct fb_fix_screeninfo *fix;
+ struct fb_var_screeninfo *var;
+ struct display *disp;
+ struct fb_info_offb *info;
+
+ for (dpy = 0; dpy < prom_num_displays; dpy++) {
+ if (!(dp = find_path_device(prom_display_paths[dpy])))
+ continue;
+
+ info = &fb_info[dpy];
+ fix = &info->fix;
+ var = &info->var;
+ disp = &info->disp;
+
+ if (!ofonly) {
+#ifdef CONFIG_FB_ATY
+ for (i = 0; i < sizeof(aty_names)/sizeof(*aty_names); i++)
+ if (!strcmp(dp->name, aty_names[i]))
+ break;
+ if (i < sizeof(aty_names)/sizeof(*aty_names)) {
+ mem_start = atyfb_of_init(mem_start, dp);
+ continue;
+ }
+#endif /* CONFIG_FB_ATY */
+ }
- if (!prom_display_path[0])
- return mem_start;
- if (!(dp = find_path_device(prom_display_path)))
- return mem_start;
-
- strncat(offb_name, dp->name, sizeof(offb_name));
- offb_name[sizeof(offb_name)-1] = '\0';
- strcpy(fb_fix.id, offb_name);
+ strcpy(fix->id, "OFfb ");
+ strncat(fix->id, dp->name, sizeof(fix->id));
+ fix->id[sizeof(fix->id)-1] = '\0';
- if ((pp = (int *)get_property(dp, "depth", &len)) != NULL
- && len == sizeof(int) && *pp != 8) {
- printk("%s: can't use depth = %d\n", dp->full_name, *pp);
- return mem_start;
- }
- if ((pp = (int *)get_property(dp, "width", &len)) != NULL
- && len == sizeof(int))
- fb_var.xres = fb_var.xres_virtual = *pp;
- if ((pp = (int *)get_property(dp, "height", &len)) != NULL
- && len == sizeof(int))
- fb_var.yres = fb_var.yres_virtual = *pp;
- if ((pp = (int *)get_property(dp, "linebytes", &len)) != NULL
- && len == sizeof(int))
- fb_fix.line_length = *pp;
- else
- fb_fix.line_length = fb_var.xres_virtual;
- fb_fix.smem_len = fb_fix.line_length*fb_var.yres;
- if ((up = (unsigned *)get_property(dp, "address", &len)) != NULL
- && len == sizeof(unsigned))
- address = (u_long)*up;
- else {
- for (i = 0; i < dp->n_addrs; ++i)
- if (dp->addrs[i].size >= len)
- break;
- if (i >= dp->n_addrs) {
- printk("no framebuffer address found for %s\n", dp->full_name);
- return mem_start;
+ if ((pp = (int *)get_property(dp, "depth", &len)) != NULL
+ && len == sizeof(int) && *pp != 8) {
+ printk("%s: can't use depth = %d\n", dp->full_name, *pp);
+ continue;
+ }
+ if ((pp = (int *)get_property(dp, "width", &len)) != NULL
+ && len == sizeof(int))
+ var->xres = var->xres_virtual = *pp;
+ if ((pp = (int *)get_property(dp, "height", &len)) != NULL
+ && len == sizeof(int))
+ var->yres = var->yres_virtual = *pp;
+ if ((pp = (int *)get_property(dp, "linebytes", &len)) != NULL
+ && len == sizeof(int))
+ fix->line_length = *pp;
+ else
+ fix->line_length = var->xres_virtual;
+ fix->smem_len = fix->line_length*var->yres;
+ if ((up = (unsigned *)get_property(dp, "address", &len)) != NULL
+ && len == sizeof(unsigned))
+ address = (u_long)*up;
+ else {
+ for (i = 0; i < dp->n_addrs; ++i)
+ if (dp->addrs[i].size >= len)
+ break;
+ if (i >= dp->n_addrs) {
+ printk("no framebuffer address found for %s\n", dp->full_name);
+ continue;
+ }
+ address = (u_long)dp->addrs[i].address;
+ }
+ fix->smem_start = ioremap(address, fix->smem_len);
+ fix->type = FB_TYPE_PACKED_PIXELS;
+ fix->type_aux = 0;
+
+ /* XXX kludge for ati */
+ if (strncmp(dp->name, "ATY,", 4) == 0) {
+ info->cmap_adr = ioremap(address + 0x7ff000, 0x1000) + 0xcc0;
+ info->cmap_data = info->cmap_adr + 1;
}
- address = (u_long)dp->addrs[i].address;
- }
- fb_fix.smem_start = ioremap(address, fb_fix.smem_len);
- fb_fix.type = FB_TYPE_PACKED_PIXELS;
- fb_fix.type_aux = 0;
-
- /* XXX kludge for ati */
- if (strncmp(dp->name, "ATY,", 4) == 0) {
- unknown_cmap_adr = ioremap(address + 0x7ff000, 0x1000) + 0xcc0;
- unknown_cmap_data = unknown_cmap_adr + 1;
- }
- fb_fix.visual = unknown_cmap_adr ? FB_VISUAL_PSEUDOCOLOR :
+ fix->visual = info->cmap_adr ? FB_VISUAL_PSEUDOCOLOR :
FB_VISUAL_STATIC_PSEUDOCOLOR;
- fb_var.xoffset = fb_var.yoffset = 0;
- fb_var.bits_per_pixel = 8;
- fb_var.grayscale = 0;
- fb_var.red.offset = fb_var.green.offset = fb_var.blue.offset = 0;
- fb_var.red.length = fb_var.green.length = fb_var.blue.length = 8;
- fb_var.red.msb_right = fb_var.green.msb_right = fb_var.blue.msb_right = 0;
- fb_var.transp.offset = fb_var.transp.length = fb_var.transp.msb_right = 0;
- fb_var.nonstd = 0;
- fb_var.activate = 0;
- fb_var.height = fb_var.width = -1;
- fb_var.accel = FB_ACCEL_NONE;
- fb_var.pixclock = 10000;
- fb_var.left_margin = fb_var.right_margin = 16;
- fb_var.upper_margin = fb_var.lower_margin = 16;
- fb_var.hsync_len = fb_var.vsync_len = 8;
- fb_var.sync = 0;
- fb_var.vmode = FB_VMODE_NONINTERLACED;
-
- disp.var = fb_var;
- disp.cmap.start = 0;
- disp.cmap.len = 0;
- disp.cmap.red = disp.cmap.green = disp.cmap.blue = disp.cmap.transp = NULL;
- disp.screen_base = fb_fix.smem_start;
- disp.visual = fb_fix.visual;
- disp.type = fb_fix.type;
- disp.type_aux = fb_fix.type_aux;
- disp.ypanstep = 0;
- disp.ywrapstep = 0;
- disp.line_length = fb_fix.line_length;
- disp.can_soft_blank = 1;
- disp.inverse = 0;
-
- strcpy(fb_info.modename, "OFfb ");
- strncat(fb_info.modename, dp->full_name, sizeof(fb_info.modename));
- fb_info.node = -1;
- fb_info.fbops = &offb_ops;
- fb_info.fbvar_num = 1;
- fb_info.fbvar = &fb_var;
- fb_info.disp = &disp;
- fb_info.fontname[0] = '\0';
- fb_info.changevar = NULL;
- fb_info.switch_con = &offbcon_switch;
- fb_info.updatevar = &offbcon_updatevar;
- fb_info.blank = &offbcon_blank;
- fb_info.setcmap = &offbcon_setcmap;
-
- err = register_framebuffer(&fb_info);
- if (err < 0)
- return mem_start;
-
- offb_set_var(&fb_var, -1);
-
- printk("Open Firmware frame buffer device on %s\n", dp->full_name);
+ var->xoffset = var->yoffset = 0;
+ var->bits_per_pixel = 8;
+ var->grayscale = 0;
+ var->red.offset = var->green.offset = var->blue.offset = 0;
+ var->red.length = var->green.length = var->blue.length = 8;
+ var->red.msb_right = var->green.msb_right = var->blue.msb_right = 0;
+ var->transp.offset = var->transp.length = var->transp.msb_right = 0;
+ var->nonstd = 0;
+ var->activate = 0;
+ var->height = var->width = -1;
+ var->accel = FB_ACCEL_NONE;
+ var->pixclock = 10000;
+ var->left_margin = var->right_margin = 16;
+ var->upper_margin = var->lower_margin = 16;
+ var->hsync_len = var->vsync_len = 8;
+ var->sync = 0;
+ var->vmode = FB_VMODE_NONINTERLACED;
+
+ disp->var = *var;
+ disp->cmap.start = 0;
+ disp->cmap.len = 0;
+ disp->cmap.red = disp->cmap.green = disp->cmap.blue = disp->cmap.transp = NULL;
+ disp->screen_base = fix->smem_start;
+ disp->visual = fix->visual;
+ disp->type = fix->type;
+ disp->type_aux = fix->type_aux;
+ disp->ypanstep = 0;
+ disp->ywrapstep = 0;
+ disp->line_length = fix->line_length;
+ disp->can_soft_blank = info->cmap_adr ? 1 : 0;
+ disp->inverse = 0;
+#ifdef CONFIG_FBCON_CFB8
+ disp->dispsw = &fbcon_cfb8;
+#else
+ disp->dispsw = NULL;
+#endif
+
+ strcpy(info->info.modename, "OFfb ");
+ strncat(info->info.modename, dp->full_name,
+ sizeof(info->info.modename));
+ info->info.node = -1;
+ info->info.fbops = &offb_ops;
+ info->info.disp = disp;
+ info->info.fontname[0] = '\0';
+ info->info.changevar = NULL;
+ info->info.switch_con = &offbcon_switch;
+ info->info.updatevar = &offbcon_updatevar;
+ info->info.blank = &offbcon_blank;
+
+ err = register_framebuffer(&info->info);
+ if (err < 0)
+ continue;
+
+ for (i = 0; i < 16; i++) {
+ int j = color_table[i];
+ info->palette[i].red = default_red[j];
+ info->palette[i].green = default_grn[j];
+ info->palette[i].blue = default_blu[j];
+ }
+ offb_set_var(var, -1, &info->info);
+
+ printk("fb%d: Open Firmware frame buffer device on %s\n",
+ GET_FB_IDX(info->info.node), dp->full_name);
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+ if (!console_fb_info) {
+ display_info.height = var->yres;
+ display_info.width = var->xres;
+ display_info.depth = 8;
+ display_info.pitch = fix->line_length;
+ display_info.mode = 0;
+ strncpy(display_info.name, dp->name, sizeof(display_info.name));
+ display_info.fb_address = iopa((unsigned long)fix->smem_start);
+ display_info.cmap_adr_address = 0;
+ display_info.cmap_data_address = 0;
+ display_info.disp_reg_address = 0;
+ /* XXX kludge for ati */
+ if (strncmp(dp->name, "ATY,", 4) == 0) {
+ display_info.disp_reg_address = iopa(address + 0x7ffc00);
+ display_info.cmap_adr_address = iopa(address + 0x7ffcc0);
+ display_info.cmap_data_address = iopa(address + 0x7ffcc1);
+ }
+ console_fb_info = &info->info;
+ console_set_cmap_ptr = offb_set_cmap;
+ }
+#endif /* CONFIG_FB_COMPAT_XPMAC) */
+ }
return mem_start;
}
-static int offbcon_switch(int con)
+ /*
+ * Setup: parse used options
+ */
+
+void offb_setup(char *options, int *ints)
+{
+ if (!options || !*options)
+ return;
+
+ if (!strcmp(options, "ofonly"))
+ ofonly = 1;
+}
+
+
+static int offbcon_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
- offb_getcolreg);
+ offb_getcolreg, info);
currcon = con;
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return 0;
}
@@ -365,7 +491,7 @@ static int offbcon_switch(int con)
* Update the `var' structure (called by fbcon.c)
*/
-static int offbcon_updatevar(int con)
+static int offbcon_updatevar(int con, struct fb_info *info)
{
/* Nothing */
return 0;
@@ -375,34 +501,42 @@ static int offbcon_updatevar(int con)
* Blank the display.
*/
-static void offbcon_blank(int blank)
+static void offbcon_blank(int blank, struct fb_info *info)
{
- /* Nothing */
-}
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
+ int i, j;
- /*
- * Set the colormap
- */
+ if (!info2->cmap_adr)
+ return;
-static int offbcon_setcmap(struct fb_cmap *cmap, int con)
-{
- return(offb_set_cmap(cmap, 1, con));
+ if (blank)
+ for (i = 0; i < 256; i++) {
+ *info2->cmap_adr = i;
+ mach_eieio();
+ for (j = 0; j < 3; j++) {
+ *info2->cmap_data = 0;
+ mach_eieio();
+ }
+ }
+ else
+ do_install_cmap(currcon, info);
}
-
/*
* Read a single color register and split it into
* colors/transparent. Return != 0 for invalid regno.
*/
static int offb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp)
+ u_int *transp, struct fb_info *info)
{
- if (!unknown_cmap_adr || regno > 255)
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
+
+ if (!info2->cmap_adr || regno > 255)
return 1;
- *red = palette[regno].red;
- *green = palette[regno].green;
- *blue = palette[regno].blue;
+ *red = info2->palette[regno].red;
+ *green = info2->palette[regno].green;
+ *blue = info2->palette[regno].blue;
return 0;
}
@@ -414,41 +548,113 @@ static int offb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
*/
static int offb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp)
+ u_int transp, struct fb_info *info)
{
- if (!unknown_cmap_adr || regno > 255)
+ struct fb_info_offb *info2 = (struct fb_info_offb *)info;
+
+ if (!info2->cmap_adr || regno > 255)
return 1;
- palette[regno].red = red;
- palette[regno].green = green;
- palette[regno].blue = blue;
- *unknown_cmap_adr = regno;
-#ifdef __powerpc__
- eieio();
-#endif
- *unknown_cmap_data = red;
-#ifdef __powerpc__
- eieio();
-#endif
- *unknown_cmap_data = green;
-#ifdef __powerpc__
- eieio();
-#endif
- *unknown_cmap_data = blue;
-#ifdef __powerpc__
- eieio();
-#endif
+ info2->palette[regno].red = red;
+ info2->palette[regno].green = green;
+ info2->palette[regno].blue = blue;
+ *info2->cmap_adr = regno;
+ mach_eieio();
+ *info2->cmap_data = red;
+ mach_eieio();
+ *info2->cmap_data = green;
+ mach_eieio();
+ *info2->cmap_data = blue;
+ mach_eieio();
return 0;
}
-static void do_install_cmap(int con)
+static void do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
- offb_setcolreg);
+ offb_setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
- &fb_display[con].var, 1, offb_setcolreg);
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, offb_setcolreg,
+ info);
}
+
+
+#ifdef CONFIG_FB_COMPAT_XPMAC
+
+ /*
+ * Backward compatibility mode for Xpmac
+ *
+ * To do:
+ *
+ * - console_setmode() should fill in a struct fb_var_screeninfo (using
+ * the MacOS video mode database) and simply call a decode_var()
+ * function, so console_setmode_ptr is no longer needed.
+ *
+ * - instead of using the console_* stuff (filled in by the frame
+ * buffer), we should use the correct struct fb_info for the
+ * foreground virtual console.
+ */
+
+int console_getmode(struct vc_mode *mode)
+{
+ *mode = display_info;
+ return 0;
+}
+
+int console_setmode(struct vc_mode *mode, int doit)
+{
+ int err;
+
+ if (console_setmode_ptr == NULL)
+ return -EINVAL;
+
+ err = (*console_setmode_ptr)(mode, doit);
+ return err;
+}
+
+static u16 palette_red[16];
+static u16 palette_green[16];
+static u16 palette_blue[16];
+
+static struct fb_cmap palette_cmap = {
+ 0, 16, palette_red, palette_green, palette_blue, NULL
+};
+
+int console_setcmap(int n_entries, unsigned char *red, unsigned char *green,
+ unsigned char *blue)
+{
+ int i, j, n;
+
+ if (console_set_cmap_ptr == NULL)
+ return -EOPNOTSUPP;
+ for (i = 0; i < n_entries; i += n) {
+ n = n_entries-i;
+ if (n > 16)
+ n = 16;
+ palette_cmap.start = i;
+ palette_cmap.len = n;
+ for (j = 0; j < n; j++) {
+ palette_cmap.red[j] = (red[i+j] << 8) | red[i+j];
+ palette_cmap.green[j] = (green[i+j] << 8) | green[i+j];
+ palette_cmap.blue[j] = (blue[i+j] << 8) | blue[i+j];
+ }
+ (*console_set_cmap_ptr)(&palette_cmap, 1, fg_console, console_fb_info);
+ }
+ return 0;
+}
+
+int console_powermode(int mode)
+{
+ if (mode == VC_POWERMODE_INQUIRY)
+ return 0;
+ if (mode < VESA_NO_BLANKING || mode > VESA_POWERDOWN)
+ return -EINVAL;
+ /* Not supported */
+ return -ENXIO;
+}
+
+#endif /* CONFIG_FB_COMPAT_XPMAC */
diff --git a/drivers/video/retz3fb.c b/drivers/video/retz3fb.c
index 18a410614..82dcc2877 100644
--- a/drivers/video/retz3fb.c
+++ b/drivers/video/retz3fb.c
@@ -21,6 +21,7 @@
*/
+#include <linux/config.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
@@ -39,6 +40,10 @@
#include <asm/pgtable.h>
#include "retz3fb.h"
+#include "fbcon.h"
+#include "fbcon-cfb8.h"
+#include "fbcon-cfb16.h"
+
/* #define DEBUG if(1) */
#define DEBUG if(0)
@@ -54,7 +59,7 @@
#define arraysize(x) (sizeof(x)/sizeof(*(x)))
-struct retz3_fb_par {
+struct retz3fb_par {
int xres;
int yres;
int xres_vir;
@@ -93,7 +98,7 @@ struct display_data {
long v_dispend; /* Horizontal Display End */
};
-static struct retz3_fb_par current_par;
+static struct retz3fb_par current_par;
static int current_par_valid = 0;
static int currcon = 0;
@@ -114,13 +119,15 @@ static struct fb_hwswitch {
/* Display Control */
- int (*encode_fix)(struct fb_fix_screeninfo *fix, struct retz3_fb_par *par);
- int (*decode_var)(struct fb_var_screeninfo *var, struct retz3_fb_par *par);
- int (*encode_var)(struct fb_var_screeninfo *var, struct retz3_fb_par *par);
+ int (*encode_fix)(struct fb_fix_screeninfo *fix, struct retz3fb_par *par);
+ int (*decode_var)(struct fb_var_screeninfo *var, struct retz3fb_par *par);
+ int (*encode_var)(struct fb_var_screeninfo *var, struct retz3fb_par *par);
int (*getcolreg)(unsigned int regno, unsigned int *red, unsigned
- int *green, unsigned int *blue, unsigned int *transp);
+ int *green, unsigned int *blue, unsigned int *transp,
+ struct fb_info *info);
int (*setcolreg)(unsigned int regno, unsigned int red, unsigned int
- green, unsigned int blue, unsigned int transp);
+ green, unsigned int blue, unsigned int transp,
+ struct fb_info *info);
void (*blank)(int blank);
} *fbhw;
@@ -129,7 +136,7 @@ static struct fb_hwswitch {
* Frame Buffer Name
*/
-static char retz3_fb_name[16] = "RetinaZ3";
+static char retz3fb_name[16] = "RetinaZ3";
static unsigned char retz3_color_table [256][4];
@@ -140,46 +147,6 @@ static volatile unsigned char *z3_regs;
/*
- * Predefined Video Mode Names
- */
-
-static char *retz3_fb_modenames[] = {
-
- /*
- * Autodetect (Default) Video Mode
- */
-
- "default",
-
- /*
- * Predefined Video Modes
- */
-
- "640x480", /* RetinaZ3 8 bpp */
- "800x600", /* RetinaZ3 8 bpp */
- "1024x768i",
- "640x480-16", /* RetinaZ3 16 bpp */
- "640x480-24", /* RetinaZ3 24 bpp */
-
- /*
- * Dummy Video Modes
- */
-
- "dummy", "dummy", "dummy", "dummy", "dummy", "dummy", "dummy",
- "dummy", "dummy", "dummy", "dummy", "dummy", "dummy", "dummy",
- "dummy", "dummy", "dummy", "dummy", "dummy", "dummy",
-
- /*
- * User Defined Video Modes
- *
- * This doesn't work yet!!
- */
-
- "user0", "user1", "user2", "user3",
- "user4", "user5", "user6", "user7"
-};
-
-/*
* A small info on how to convert XFree86 timing values into fb
* timings - by Frank Neumann:
*
@@ -217,131 +184,124 @@ under "programs/Xserver/hw/xfree86/doc/modeDB.txt".
*/
/*
- * Predefined Video Mode Definitions
+ * Predefined Video Modes
*/
-static struct fb_var_screeninfo retz3_fb_predefined[] = {
-
- /*
- * Autodetect (Default) Video Mode
- */
-
- { 0, },
-
- /*
- * Predefined Video Modes
- */
-
- /*
- * NB: it is very important to adjust the pixel-clock to the color-depth.
- */
-
- {
- 640, 480, 640, 480, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_RETINAZ3, 38461, 28, 32, 12, 10, 96, 2,
- FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- },
- /*
- ModeLine "800x600" 36 800 824 896 1024 600 601 603 625
- < name > DCF HR SH1 SH2 HFL VR SV1 SV2 VFL
- */
- {
- /* 800 x 600, 8 bpp */
- 800, 600, 800, 600, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_RETINAZ3, 27778, 64, 24, 22, 1, 120, 2,
- FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- },
- /*
- ModeLine "1024x768i" 45 1024 1064 1224 1264 768 777 785 817 interlace
- < name > DCF HR SH1 SH2 HFL VR SV1 SV2 VFL
- */
- {
- /* 1024 x 768, 8 bpp, interlaced */
- 1024, 768, 1024, 768, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_RETINAZ3, 22222, 40, 40, 32, 9, 160, 8,
- FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_INTERLACED
- },
- {
- 640, 480, 640, 480, 0, 0, 16, 0,
- {11, 5, 0}, {5, 6, 0}, {0, 5, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_RETINAZ3, 38461/2, 28, 32, 12, 10, 96, 2,
- FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- },
- {
- 640, 480, 640, 480, 0, 0, 24, 0,
- {8, 8, 8}, {8, 8, 8}, {8, 8, 8}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_RETINAZ3, 38461/3, 28, 32, 12, 10, 96, 2,
- FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
- },
-
- /*
- * Dummy Video Modes
- */
-
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, },
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, },
- { 0, }, { 0, },
-
- /*
- * User Defined Video Modes
- */
-
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }
+static struct fb_videomode retz3fb_predefined[] __initdata = {
+ /*
+ * NB: it is very important to adjust the pixel-clock to the color-depth.
+ */
+
+ {
+ "640x480", { /* 640x480, 8 bpp */
+ 640, 480, 640, 480, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NCR77C32BLT, 38461, 28, 32, 12, 10, 96, 2,
+ FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ },
+ /*
+ ModeLine "800x600" 36 800 824 896 1024 600 601 603 625
+ < name > DCF HR SH1 SH2 HFL VR SV1 SV2 VFL
+ */
+ {
+ "800x600", { /* 800x600, 8 bpp */
+ 800, 600, 800, 600, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NCR77C32BLT, 27778, 64, 24, 22, 1, 120, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ },
+ /*
+ ModeLine "1024x768i" 45 1024 1064 1224 1264 768 777 785 817 interlace
+ < name > DCF HR SH1 SH2 HFL VR SV1 SV2 VFL
+ */
+ {
+ "1024x768i", { /* 1024x768, 8 bpp, interlaced */
+ 1024, 768, 1024, 768, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NCR77C32BLT, 22222, 40, 40, 32, 9, 160, 8,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_INTERLACED
+ }
+ }, {
+ "640x480-16", { /* 640x480, 16 bpp */
+ 640, 480, 640, 480, 0, 0, 16, 0,
+ {11, 5, 0}, {5, 6, 0}, {0, 5, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NCR77C32BLT, 38461/2, 28, 32, 12, 10, 96, 2,
+ FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "640x480-24", { /* 640x480, 24 bpp */
+ 640, 480, 640, 480, 0, 0, 24, 0,
+ {8, 8, 8}, {8, 8, 8}, {8, 8, 8}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NCR77C32BLT, 38461/3, 28, 32, 12, 10, 96, 2,
+ FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ },
};
-#define NUM_TOTAL_MODES arraysize(retz3_fb_predefined)
-#define NUM_PREDEF_MODES 5
+#define NUM_TOTAL_MODES arraysize(retz3fb_predefined)
+static struct fb_var_screeninfo retz3fb_default;
static int z3fb_inverse = 0;
-static int z3fb_mode = 0;
+static int z3fb_mode __initdata = 0;
/*
* Interface used by the world
*/
-void retz3_video_setup(char *options, int *ints);
-
-static int retz3_fb_open(int fbidx);
-static int retz3_fb_release(int fbidx);
-static int retz3_fb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int retz3_fb_get_var(struct fb_var_screeninfo *var, int con);
-static int retz3_fb_set_var(struct fb_var_screeninfo *var, int con);
-static int retz3_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int retz3_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int retz3_fb_pan_display(struct fb_var_screeninfo *var, int con);
-static int retz3_fb_ioctl(struct inode *inode, struct file *file,
- unsigned int cmd, unsigned long arg, int con);
+void retz3fb_setup(char *options, int *ints);
+
+static int retz3fb_open(struct fb_info *info);
+static int retz3fb_release(struct fb_info *info);
+static int retz3fb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int retz3fb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int retz3fb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int retz3fb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int retz3fb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int retz3fb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int retz3fb_ioctl(struct inode *inode, struct file *file,
+ unsigned int cmd, unsigned long arg, int con,
+ struct fb_info *info);
/*
* Interface to the low level console driver
*/
-unsigned long retz3_fb_init(unsigned long mem_start);
-static int z3fb_switch(int con);
-static int z3fb_updatevar(int con);
-static void z3fb_blank(int blank);
-static int z3fb_setcmap(struct fb_cmap *cmap, int con);
+unsigned long retz3fb_init(unsigned long mem_start);
+static int z3fb_switch(int con, struct fb_info *info);
+static int z3fb_updatevar(int con, struct fb_info *info);
+static void z3fb_blank(int blank, struct fb_info *info);
+
+
+/*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static struct display_switch fbcon_retz3_8;
+#endif
/*
* Accelerated Functions used by the low level console driver
*/
-void retz3_bitblt(struct fb_var_screeninfo *scr,
- unsigned short curx, unsigned short cury, unsigned
- short destx, unsigned short desty, unsigned short
- width, unsigned short height, unsigned short cmd,
- unsigned short mask);
-void retz3_fill(unsigned short x, unsigned short y, unsigned short
- width, unsigned short height, unsigned short mode,
- unsigned short color);
+static void retz3_bitblt(struct fb_var_screeninfo *scr,
+ unsigned short curx, unsigned short cury, unsigned
+ short destx, unsigned short desty, unsigned short
+ width, unsigned short height, unsigned short cmd,
+ unsigned short mask);
/*
* Hardware Specific Routines
@@ -349,17 +309,17 @@ void retz3_fill(unsigned short x, unsigned short y, unsigned short
static int retz3_init(void);
static int retz3_encode_fix(struct fb_fix_screeninfo *fix,
- struct retz3_fb_par *par);
+ struct retz3fb_par *par);
static int retz3_decode_var(struct fb_var_screeninfo *var,
- struct retz3_fb_par *par);
+ struct retz3fb_par *par);
static int retz3_encode_var(struct fb_var_screeninfo *var,
- struct retz3_fb_par *par);
+ struct retz3fb_par *par);
static int retz3_getcolreg(unsigned int regno, unsigned int *red,
unsigned int *green, unsigned int *blue,
- unsigned int *transp);
+ unsigned int *transp, struct fb_info *info);
static int retz3_setcolreg(unsigned int regno, unsigned int red,
unsigned int green, unsigned int blue,
- unsigned int transp);
+ unsigned int transp, struct fb_info *info);
static void retz3_blank(int blank);
@@ -367,13 +327,11 @@ static void retz3_blank(int blank);
* Internal routines
*/
-static void retz3_fb_get_par(struct retz3_fb_par *par);
-static void retz3_fb_set_par(struct retz3_fb_par *par);
+static void retz3fb_get_par(struct retz3fb_par *par);
+static void retz3fb_set_par(struct retz3fb_par *par);
static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive);
-static void do_install_cmap(int con);
-/*
-static void retz3_fb_set_disp(int con);
-*/
+static void do_install_cmap(int con, struct fb_info *info);
+static void retz3fb_set_disp(int con, struct fb_info *info);
static int get_video_mode(const char *name);
@@ -397,7 +355,7 @@ static unsigned short find_fq(unsigned int freq)
else if (freq <= 250000000)
n2 = 0;
else
- return(0);
+ return 0;
do {
@@ -424,10 +382,12 @@ static unsigned short find_fq(unsigned int freq)
static int retz3_set_video(struct fb_var_screeninfo *var,
- struct retz3_fb_par *par)
+ struct retz3fb_par *par)
{
+#if 0
float freq_f;
- long freq;
+#endif
+ unsigned int freq;
int xres, hfront, hsync, hback;
int yres, vfront, vsync, vback;
@@ -478,7 +438,7 @@ static int retz3_set_video(struct fb_var_screeninfo *var,
vback = var->upper_margin;
}
- data.h_total = (hback / 8) + (xres / 8)
+ data.h_total = (hback / 8) + (xres / 8)
+ (hfront / 8) + (hsync / 8) - 1 /* + 1 */;
data.h_dispend = ((xres + bpp - 1)/ 8) - 1;
data.h_bstart = xres / 8 /* + 1 */;
@@ -736,8 +696,13 @@ static int retz3_set_video(struct fb_var_screeninfo *var,
/*
* Convert from ps to Hz.
*/
+#if 0
freq_f = (1.0/(float)var->pixclock) * 1000000000;
- freq = ((long)freq_f) * 1000;
+ freq = ((unsigned int)freq_f) * 1000;
+#else
+ freq = 2000000000 / var->pixclock;
+ freq = freq * 500;
+#endif
best_freq = find_fq(freq);
pll_w(0x02, best_freq);
@@ -791,7 +756,7 @@ static int retz3_set_video(struct fb_var_screeninfo *var,
*/
switch (bpp){
case 8:
- reg_w(0x83c6, 0x00);
+ reg_w(0x83c6, 0x00);
break;
case 16:
reg_w(0x83c6, 0x60);
@@ -805,7 +770,7 @@ static int retz3_set_video(struct fb_var_screeninfo *var,
reg_w(VDAC_ADDRESS, 0x00);
- seq_w(SEQ_MAP_MASK, 0x0f );
+ seq_w(SEQ_MAP_MASK, 0x0f );
return 0;
}
@@ -854,8 +819,8 @@ static int retz3_init(void)
}
#endif
- retz3_setcolreg (255, 56, 100, 160, 0);
- retz3_setcolreg (254, 0, 0, 0, 0);
+ retz3_setcolreg (255, 56, 100, 160, 0, NULL /* unused */);
+ retz3_setcolreg (254, 0, 0, 0, 0, NULL /* unused */);
return 0;
}
@@ -867,11 +832,11 @@ static int retz3_init(void)
*/
static int retz3_encode_fix(struct fb_fix_screeninfo *fix,
- struct retz3_fb_par *par)
+ struct retz3fb_par *par)
{
short i;
- strcpy(fix->id, retz3_fb_name);
+ strcpy(fix->id, retz3fb_name);
fix->smem_start = (char *)z3_fbmem;
fix->smem_len = z3_size;
fix->mmio_start = (unsigned char *)z3_regs;
@@ -889,6 +854,8 @@ static int retz3_encode_fix(struct fb_fix_screeninfo *fix,
fix->ywrapstep = 0;
fix->line_length = 0;
+ fix->accel = FB_ACCEL_NCR77C32BLT;
+
for (i = 0; i < arraysize(fix->reserved); i++)
fix->reserved[i] = 0;
@@ -902,7 +869,7 @@ static int retz3_encode_fix(struct fb_fix_screeninfo *fix,
*/
static int retz3_decode_var(struct fb_var_screeninfo *var,
- struct retz3_fb_par *par)
+ struct retz3fb_par *par)
{
par->xres = var->xres;
par->yres = var->yres;
@@ -934,7 +901,7 @@ static int retz3_decode_var(struct fb_var_screeninfo *var,
*/
static int retz3_encode_var(struct fb_var_screeninfo *var,
- struct retz3_fb_par *par)
+ struct retz3fb_par *par)
{
short i;
@@ -959,7 +926,7 @@ static int retz3_encode_var(struct fb_var_screeninfo *var,
var->height = -1;
var->width = -1;
- var->accel = FB_ACCEL_RETINAZ3;
+ var->accel = FB_ACCEL_NCR77C32BLT;
var->pixclock = par->pixclock;
@@ -987,7 +954,7 @@ static int retz3_encode_var(struct fb_var_screeninfo *var,
static int retz3_setcolreg(unsigned int regno, unsigned int red,
unsigned int green, unsigned int blue,
- unsigned int transp)
+ unsigned int transp, struct fb_info *info)
{
/* We'll get to this */
@@ -1015,7 +982,7 @@ static int retz3_setcolreg(unsigned int regno, unsigned int red,
static int retz3_getcolreg(unsigned int regno, unsigned int *red,
unsigned int *green, unsigned int *blue,
- unsigned int *transp)
+ unsigned int *transp, struct fb_info *info)
{
if (regno > 255)
return 1;
@@ -1052,11 +1019,11 @@ void retz3_blank(int blank)
}
-void retz3_bitblt (struct fb_var_screeninfo *var,
- unsigned short srcx, unsigned short srcy, unsigned
- short destx, unsigned short desty, unsigned short
- width, unsigned short height, unsigned short cmd,
- unsigned short mask)
+static void retz3_bitblt (struct fb_var_screeninfo *var,
+ unsigned short srcx, unsigned short srcy,
+ unsigned short destx, unsigned short desty,
+ unsigned short width, unsigned short height,
+ unsigned short cmd, unsigned short mask)
{
volatile unsigned long *acm = (unsigned long *) (z3_mem + ACM_OFFSET);
@@ -1129,7 +1096,7 @@ void retz3_bitblt (struct fb_var_screeninfo *var,
*(acm + ACM_CONTROL/4) = tmp;
tmp = width | (height << 16);
-
+
*(acm + ACM_BITMAP_DIMENSION/4) = cpu_to_le32(tmp);
*(((volatile unsigned char *)acm) + ACM_START_STATUS) = 0x00;
@@ -1154,20 +1121,10 @@ void retz3_bitblt (struct fb_var_screeninfo *var,
}
#if 0
-void retz3_fill (unsigned short x, unsigned short y, unsigned
- short width, unsigned short height,
- unsigned short mode, unsigned short color)
-{
-
-}
-#endif
-
-
-#if 0
/*
* Move cursor to x, y
*/
-void retz3_MoveCursor (unsigned short x, unsigned short y)
+static void retz3_MoveCursor (unsigned short x, unsigned short y)
{
/* Guess we gotta deal with the cursor at some point */
}
@@ -1189,16 +1146,16 @@ static struct fb_hwswitch retz3_switch = {
* Fill the hardware's `par' structure.
*/
-static void retz3_fb_get_par(struct retz3_fb_par *par)
+static void retz3fb_get_par(struct retz3fb_par *par)
{
if (current_par_valid)
*par = current_par;
else
- fbhw->decode_var(&retz3_fb_predefined[z3fb_mode], par);
+ fbhw->decode_var(&retz3fb_default, par);
}
-static void retz3_fb_set_par(struct retz3_fb_par *par)
+static void retz3fb_set_par(struct retz3fb_par *par)
{
current_par = *par;
current_par_valid = 1;
@@ -1208,7 +1165,7 @@ static void retz3_fb_set_par(struct retz3_fb_par *par)
static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
{
int err, activate;
- struct retz3_fb_par par;
+ struct retz3fb_par par;
if ((err = fbhw->decode_var(var, &par)))
return err;
@@ -1217,7 +1174,7 @@ static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
/* XXX ... what to do about isactive ? */
if ((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW && isactive)
- retz3_fb_set_par(&par);
+ retz3fb_set_par(&par);
fbhw->encode_var(var, &par);
var->activate = activate;
@@ -1227,17 +1184,17 @@ static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
}
-static void do_install_cmap(int con)
+static void do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
&fb_display[con].var, 1,
- fbhw->setcolreg);
+ fbhw->setcolreg, info);
}
@@ -1245,7 +1202,7 @@ static void do_install_cmap(int con)
* Open/Release the frame buffer device
*/
-static int retz3_fb_open(int fbidx)
+static int retz3fb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -1255,7 +1212,7 @@ static int retz3_fb_open(int fbidx)
return 0;
}
-static int retz3_fb_release(int fbidx)
+static int retz3fb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return 0;
@@ -1266,13 +1223,14 @@ static int retz3_fb_release(int fbidx)
* Get the Fixed Part of the Display
*/
-static int retz3_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
+static int retz3fb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
{
- struct retz3_fb_par par;
+ struct retz3fb_par par;
int error = 0;
if (con == -1)
- retz3_fb_get_par(&par);
+ retz3fb_get_par(&par);
else
error = fbhw->decode_var(&fb_display[con].var, &par);
return(error ? error : fbhw->encode_fix(fix, &par));
@@ -1283,13 +1241,14 @@ static int retz3_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
* Get the User Defined Part of the Display
*/
-static int retz3_fb_get_var(struct fb_var_screeninfo *var, int con)
+static int retz3fb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
- struct retz3_fb_par par;
+ struct retz3fb_par par;
int error = 0;
if (con == -1) {
- retz3_fb_get_par(&par);
+ retz3fb_get_par(&par);
error = fbhw->encode_var(var, &par);
} else
*var = fb_display[con].var;
@@ -1298,7 +1257,7 @@ static int retz3_fb_get_var(struct fb_var_screeninfo *var, int con)
#if 1
-static void retz3_fb_set_disp(int con)
+static void retz3fb_set_disp(int con, struct fb_info *info)
{
struct fb_fix_screeninfo fix;
struct display *display;
@@ -1308,7 +1267,7 @@ static void retz3_fb_set_disp(int con)
else
display = &disp; /* used during initialization */
- retz3_fb_get_fix(&fix, con);
+ retz3fb_get_fix(&fix, con, info);
if (con == -1)
con = 0;
@@ -1321,6 +1280,21 @@ static void retz3_fb_set_disp(int con)
display->ywrapstep = fix.ywrapstep;
display->can_soft_blank = 1;
display->inverse = z3fb_inverse;
+ switch (display->var.bits_per_pixel) {
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_retz3_8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ case 16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ break;
+ }
}
#endif
@@ -1328,7 +1302,8 @@ static void retz3_fb_set_disp(int con)
* Set the User Defined Part of the Display
*/
-static int retz3_fb_set_var(struct fb_var_screeninfo *var, int con)
+static int retz3fb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
int err, oldxres, oldyres, oldvxres, oldvyres, oldbpp;
struct display *display;
@@ -1359,7 +1334,7 @@ static int retz3_fb_set_var(struct fb_var_screeninfo *var, int con)
oldbpp != var->bits_per_pixel) {
struct fb_fix_screeninfo fix;
- retz3_fb_get_fix(&fix, con);
+ retz3fb_get_fix(&fix, con, info);
display->screen_base = fix.smem_start;
display->visual = fix.visual;
@@ -1370,8 +1345,23 @@ static int retz3_fb_set_var(struct fb_var_screeninfo *var, int con)
display->line_length = fix.line_length;
display->can_soft_blank = 1;
display->inverse = z3fb_inverse;
+ switch (display->var.bits_per_pixel) {
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_retz3_8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ case 16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ break;
+ }
/*
- retz3_fb_set_disp(con);
+ retz3fb_set_disp(con, info);
*/
if (fb_info.changevar)
(*fb_info.changevar)(con);
@@ -1380,7 +1370,7 @@ static int retz3_fb_set_var(struct fb_var_screeninfo *var, int con)
if (oldbpp != var->bits_per_pixel) {
if ((err = fb_alloc_cmap(&display->cmap, 0, 0)))
return err;
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
}
return 0;
@@ -1391,15 +1381,16 @@ static int retz3_fb_set_var(struct fb_var_screeninfo *var, int con)
* Get the Colormap
*/
-static int retz3_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int retz3fb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
if (con == currcon) /* current console? */
return(fb_get_cmap(cmap, &fb_display[con].var, kspc,
- fbhw->getcolreg));
+ fbhw->getcolreg, info));
else if (fb_display[con].cmap.len) /* non default colormap? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return 0;
}
@@ -1409,7 +1400,8 @@ static int retz3_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
* Set the Colormap
*/
-static int retz3_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int retz3fb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
int err;
@@ -1421,7 +1413,7 @@ static int retz3_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
}
if (con == currcon) /* current console? */
return(fb_set_cmap(cmap, &fb_display[con].var, kspc,
- fbhw->setcolreg));
+ fbhw->setcolreg, info));
else
fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
return 0;
@@ -1434,7 +1426,8 @@ static int retz3_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
* This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
*/
-static int retz3_fb_pan_display(struct fb_var_screeninfo *var, int con)
+static int retz3fb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
return -EINVAL;
}
@@ -1444,21 +1437,22 @@ static int retz3_fb_pan_display(struct fb_var_screeninfo *var, int con)
* RetinaZ3 Frame Buffer Specific ioctls
*/
-static int retz3_fb_ioctl(struct inode *inode, struct file *file,
- unsigned int cmd, unsigned long arg, int con)
+static int retz3fb_ioctl(struct inode *inode, struct file *file,
+ unsigned int cmd, unsigned long arg, int con,
+ struct fb_info *info)
{
return -EINVAL;
}
-static struct fb_ops retz3_fb_ops = {
- retz3_fb_open, retz3_fb_release, retz3_fb_get_fix, retz3_fb_get_var,
- retz3_fb_set_var, retz3_fb_get_cmap, retz3_fb_set_cmap,
- retz3_fb_pan_display, retz3_fb_ioctl
+static struct fb_ops retz3fb_ops = {
+ retz3fb_open, retz3fb_release, retz3fb_get_fix, retz3fb_get_var,
+ retz3fb_set_var, retz3fb_get_cmap, retz3fb_set_cmap,
+ retz3fb_pan_display, NULL, retz3fb_ioctl
};
-__initfunc(void retz3_video_setup(char *options, int *ints))
+__initfunc(void retz3fb_setup(char *options, int *ints))
{
char *this_opt;
@@ -1467,7 +1461,7 @@ __initfunc(void retz3_video_setup(char *options, int *ints))
if (!options || !*options)
return;
- for (this_opt = strtok(options, ","); this_opt;
+ for (this_opt = strtok(options, ","); this_opt;
this_opt = strtok(NULL, ",")){
if (!strcmp(this_opt, "inverse")) {
z3fb_inverse = 1;
@@ -1484,14 +1478,14 @@ __initfunc(void retz3_video_setup(char *options, int *ints))
* Initialization
*/
-__initfunc(unsigned long retz3_fb_init(unsigned long mem_start))
+__initfunc(unsigned long retz3fb_init(unsigned long mem_start))
{
int err;
unsigned long board_addr, board_size;
unsigned int key;
const struct ConfigDev *cd;
- struct retz3_fb_par par;
+ struct retz3fb_par par;
if (!(key = zorro_find(ZORRO_PROD_MACROSYSTEMS_RETINA_Z3, 0, 0)))
return mem_start;
@@ -1511,43 +1505,38 @@ __initfunc(unsigned long retz3_fb_init(unsigned long mem_start))
z3_size = 0x00400000; /* 4 MB */
- memset ((char*)z3_fbmem, 0, z3_size);
-
fbhw = &retz3_switch;
fbhw->init();
- strcpy(fb_info.modename, retz3_fb_name);
+ strcpy(fb_info.modename, retz3fb_name);
fb_info.changevar = NULL;
fb_info.node = -1;
- fb_info.fbops = &retz3_fb_ops;
- fb_info.fbvar_num = NUM_TOTAL_MODES;
- fb_info.fbvar = retz3_fb_predefined;
+ fb_info.fbops = &retz3fb_ops;
fb_info.disp = &disp;
fb_info.switch_con = &z3fb_switch;
fb_info.updatevar = &z3fb_updatevar;
fb_info.blank = &z3fb_blank;
- fb_info.setcmap = &z3fb_setcmap;
err = register_framebuffer(&fb_info);
if (err < 0)
return mem_start;
if (z3fb_mode == -1)
- z3fb_mode = 1;
+ retz3fb_default = retz3fb_predefined[0].var;
- fbhw->decode_var(&retz3_fb_predefined[z3fb_mode], &par);
- fbhw->encode_var(&retz3_fb_predefined[0], &par);
+ fbhw->decode_var(&retz3fb_default, &par);
+ fbhw->encode_var(&retz3fb_default, &par);
- do_fb_set_var(&retz3_fb_predefined[0], 0);
- retz3_fb_get_var(&disp.var, -1);
+ do_fb_set_var(&retz3fb_default, 0);
+ retz3fb_get_var(&disp.var, -1, &fb_info);
- retz3_fb_set_disp(-1);
+ retz3fb_set_disp(-1, &fb_info);
- do_install_cmap(0);
+ do_install_cmap(0, &fb_info);
- printk("%s frame buffer device, using %ldK of video memory\n",
- fb_info.modename, z3_size>>10);
+ printk("fb%d: %s frame buffer device, using %ldK of video memory\n",
+ GET_FB_IDX(fb_info.node), fb_info.modename, z3_size>>10);
/* TODO: This driver cannot be unloaded yet */
MOD_INC_USE_COUNT;
@@ -1556,17 +1545,18 @@ __initfunc(unsigned long retz3_fb_init(unsigned long mem_start))
}
-static int z3fb_switch(int con)
+static int z3fb_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap,
- &fb_display[currcon].var, 1, fbhw->getcolreg);
+ &fb_display[currcon].var, 1, fbhw->getcolreg,
+ info);
do_fb_set_var(&fb_display[con].var, 1);
currcon = con;
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return 0;
}
@@ -1578,7 +1568,7 @@ static int z3fb_switch(int con)
* Since it's called by a kernel driver, no range checking is done.
*/
-static int z3fb_updatevar(int con)
+static int z3fb_updatevar(int con, struct fb_info *info)
{
return 0;
}
@@ -1588,33 +1578,23 @@ static int z3fb_updatevar(int con)
* Blank the display.
*/
-static void z3fb_blank(int blank)
+static void z3fb_blank(int blank, struct fb_info *info)
{
fbhw->blank(blank);
}
/*
- * Set the colormap
- */
-
-static int z3fb_setcmap(struct fb_cmap *cmap, int con)
-{
- return(retz3_fb_set_cmap(cmap, 1, con));
-}
-
-
-/*
* Get a Video Mode
*/
-static int get_video_mode(const char *name)
+__initfunc(static int get_video_mode(const char *name))
{
short i;
- for (i = 1; i <= NUM_PREDEF_MODES; i++)
- if (!strcmp(name, retz3_fb_modenames[i])){
- retz3_fb_predefined[0] = retz3_fb_predefined[i];
+ for (i = 0; i <= NUM_TOTAL_MODES; i++)
+ if (!strcmp(name, retz3fb_predefined[i].name)){
+ retz3fb_default = retz3fb_predefined[i].var;
return i;
}
return -1;
@@ -1624,7 +1604,7 @@ static int get_video_mode(const char *name)
#ifdef MODULE
int init_module(void)
{
- return(retz3_fb_init(NULL));
+ return(retz3fb_init(NULL));
}
void cleanup_module(void)
@@ -1636,11 +1616,60 @@ void cleanup_module(void)
unregister_framebuffer(&fb_info);
/* TODO: clean up ... */
}
-#endif /* MODULE */
+#endif
/*
- * Visible symbols for modules
+ * Text console acceleration
*/
-EXPORT_SYMBOL(retz3_bitblt);
+#ifdef CONFIG_FBCON_CFB8
+static void fbcon_retz3_8_bmove(struct display *p, int sy, int sx, int dy, int dx,
+ int height, int width)
+{
+ int fontwidth = p->fontwidth;
+
+ sx *= fontwidth;
+ dx *= fontwidth;
+ width *= fontwidth;
+
+ retz3_bitblt(&p->var,
+ (unsigned short)sx,
+ (unsigned short)(sy*p->fontheight),
+ (unsigned short)dx,
+ (unsigned short)(dy*p->fontheight),
+ (unsigned short)width,
+ (unsigned short)(height*p->fontheight),
+ Z3BLTcopy,
+ 0xffff);
+}
+
+static void fbcon_retz3_8_clear(struct vc_data *conp, struct display *p, int
+ sy, int sx, int height, int width)
+{
+ unsigned short col;
+ int fontwidth = p->fontwidth;
+
+ sx *= fontwidth;
+ width *= fontwidth;
+
+ col = attr_bgcol_ec(p, conp);
+ col &= 0xff;
+ col |= (col << 8);
+
+ retz3_bitblt(&p->var,
+ (unsigned short)sx,
+ (unsigned short)(sy*p->fontheight),
+ (unsigned short)sx,
+ (unsigned short)(sy*p->fontheight),
+ (unsigned short)width,
+ (unsigned short)(height*p->fontheight),
+ Z3BLTset,
+ col);
+}
+
+static struct display_switch fbcon_retz3_8 = {
+ fbcon_cfb8_setup, fbcon_retz3_8_bmove, fbcon_retz3_8_clear,
+ fbcon_cfb8_putc, fbcon_cfb8_putcs, fbcon_cfb8_revc
+};
+#endif
diff --git a/drivers/video/skeletonfb.c b/drivers/video/skeletonfb.c
new file mode 100644
index 000000000..3f795cd63
--- /dev/null
+++ b/drivers/video/skeletonfb.c
@@ -0,0 +1,388 @@
+/*
+ * linux/drivers/video/skeletonfb.c -- Skeleton for a frame buffer device
+ *
+ * Created 28 Dec 1997 by Geert Uytterhoeven
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file README.legal in the main directory of this archive
+ * for more details.
+ */
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/mm.h>
+#include <linux/tty.h>
+#include <linux/malloc.h>
+#include <linux/delay.h>
+#include <linux/fb.h>
+
+#include "fbcon.h"
+
+
+ /*
+ * This is just simple sample code.
+ *
+ * No warranty that it actually compiles.
+ * Even less warranty that it actually works :-)
+ */
+
+
+struct xxxfb_info {
+ /*
+ * Choose _one_ of the two alternatives:
+ *
+ * 1. Use the generic frame buffer operations (fbgen_*).
+ */
+ struct fb_info_gen gen;
+ /*
+ * 2. Provide your own frame buffer operations.
+ */
+ struct fb_info info;
+
+ /* Here starts the frame buffer device dependent part */
+ /* You can use this to store e.g. the board number if you support */
+ /* multiple boards */
+};
+
+
+struct xxxfb_par {
+ /*
+ * The hardware specific data in this structure uniquely defines a video
+ * mode.
+ *
+ * If your hardware supports only one video mode, you can leave it empty.
+ */
+};
+
+
+ /*
+ * If your driver supports multiple boards, you should make these arrays,
+ * or allocate them dynamically (using mem_start for builtin drivers, and
+ * kmalloc() for loaded modules).
+ */
+
+static struct xxxfb_info fb_info;
+static struct xxxfb_par current_par;
+static int current_par_valid = 0;
+static struct display disp;
+
+static struct fb_var_screeninfo default_var;
+
+static int currcon = 0;
+static int inverse = 0;
+
+
+/* ------------------- chipset specific functions -------------------------- */
+
+
+static void xxx_detect(void)
+{
+ /*
+ * This function should detect the current video mode settings and store
+ * it as the default video mode
+ */
+
+ /* ... */
+ xxx_get_par(&par);
+ xxx_encode_var(&default_var, &par);
+}
+
+static int xxx_encode_fix(struct fb_fix_screeninfo *fix, struct xxxfb_par *par,
+ const struct fb_info *fb_info)
+{
+ /*
+ * This function should fill in the 'fix' structure based on the values
+ * in the `par' structure.
+ */
+
+ /* ... */
+ return 0;
+}
+
+static int xxx_decode_var(struct fb_var_screeninfo *var, struct xxxfb_par *par,
+ const struct fb_info *fb_info)
+{
+ /*
+ * Get the video params out of 'var'. If a value doesn't fit, round it up,
+ * if it's too big, return -EINVAL.
+ *
+ * Suggestion: Round up in the following order: bits_per_pixel, xres,
+ * yres, xres_virtual, yres_virtual, xoffset, yoffset, grayscale,
+ * bitfields, horizontal timing, vertical timing.
+ */
+
+ /* ... */
+
+ /* pixclock in picos, htotal in pixels, vtotal in scanlines */
+ if (!fbmon_valid_timings(pixclock, htotal, vtotal, info))
+ return -EINVAL;
+
+ return 0;
+}
+
+static int xxx_encode_var(struct fb_var_screeninfo *var, struct xxxfb_par *par,
+ const struct fb_info *fb_info)
+{
+ /*
+ * Fill the 'var' structure based on the values in 'par' and maybe other
+ * values read out of the hardware.
+ */
+
+ /* ... */
+ return 0;
+}
+
+static void xxx_get_par(struct xxxfb_par *par, const struct fb_info *fb_info)
+{
+ /*
+ * Fill the hardware's 'par' structure.
+ */
+
+ if (current_par_valid)
+ *par = current_par;
+ else {
+ /* ... */
+ }
+}
+
+static void xxx_set_par(struct xxxfb_par *par, const struct fb_info *fb_info)
+{
+ /*
+ * Set the hardware according to 'par'.
+ */
+
+ current_par = *par;
+ current_par_valid = 1;
+ /* ... */
+}
+
+static int xxx_getcolreg(unsigned regno, unsigned *red, unsigned *green,
+ unsigned *blue, unsigned *transp,
+ const struct fb_info *fb_info)
+{
+ /*
+ * Read a single color register and split it into colors/transparent.
+ * Return != 0 for invalid regno.
+ */
+
+ /* ... */
+ return 0;
+}
+
+static int xxx_setcolreg(unsigned regno, unsigned red, unsigned green,
+ unsigned blue, unsigned transp,
+ const struct fb_info *fb_info)
+{
+ /*
+ * Set a single color register. The values supplied are already rounded
+ * down to the hardware's capabilities (according to the entries in the
+ * `var' structure). Return != 0 for invalid regno.
+ */
+
+ if (regno < 16) {
+ /*
+ * Make the first 16 colors of the palette available to fbcon
+ */
+ if (is_cfb15) /* RGB 555 */
+ fbcon_cfb15_cmap[regno] = be16_to_cpu((red << 10) | (green << 5) |
+ blue);
+ if (is_cfb16) /* RGB 565 */
+ fbcon_cfb16_cmap[regno] = be16_to_cpu((red << 11) | (green << 5) |
+ blue);
+ if (is_cfb24) /* RGB 888 */
+ fbcon_cfb24_cmap[regno] = be32_to_cpu((red << 16) | (green << 8) |
+ blue);
+ if (is_cfb32) /* RGBA 8888 */
+ fbcon_cfb32_cmap[regno] = be32_to_cpu((red << 24) | (green << 16) |
+ (blue << 8) | transp);
+ }
+ /* ... */
+ return 0;
+}
+
+static int xxx_pan_display(struct fb_var_screeninfo *var,
+ struct xxxfb_par *par,
+ const struct fb_info *fb_info)
+{
+ /*
+ * 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 int xxx_blank(int blank_mode, const struct fb_info *fb_info)
+{
+ /*
+ * 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
+ */
+
+ /* ... */
+ return 0;
+}
+
+static struct display_switch *xxx_get_dispsw(const void *par,
+ struct fb_info_gen *info)
+{
+ /*
+ * Return a pointer to appropriate low level text console operations for
+ * the video mode `par' of your video hardware. These can be generic
+ * software routines, or hardware accelerated routines specifically
+ * tailored for your hardware.
+ * If you don't have any appropriate operations, simple fill in the NULL
+ * pointer, and there will be no text output.
+ */
+#ifdef CONFIG_FBCON_CFB8
+ if (is_cfb8)
+ return &fbcon_cfb8;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ if (is_cfb16)
+ return &fbcon_cfb16;
+#endif
+#ifdef CONFIG_FBCON_CFB32
+ if (is_cfb32)
+ return &fbcon_cfb32;
+#endif
+ return NULL;
+}
+
+
+/* ------------ Interfaces to hardware functions ------------ */
+
+
+struct fbgen_hwswitch xxx_switch = {
+ xxx_detect, xxx_encode_fix, xxx_decode_var, xxx_encode_var, xxx_get_par,
+ xxx_set_par, xxx_getcolreg, xxx_setcolreg, xxx_blank, xxx_dispsw
+};
+
+
+
+/* ------------ Hardware Independant Functions ------------ */
+
+
+ /*
+ * Initialization
+ */
+
+__initfunc(unsigned long xxxfb_init(unsigned long mem_start))
+{
+ int err;
+ struct fb_var_screeninfo var;
+
+ fb_info.fbhw = &xxx_switch;
+ fbhw->detect();
+ strcpy(fb_info.modename, "XXX");
+ fb_info.changevar = NULL;
+ fb_info.node = -1;
+ fb_info.fbops = &xxxfb_ops;
+ fb_info.disp = disp;
+ fb_info.switch_con = &xxxfb_switch;
+ fb_info.updatevar = &xxxfb_update_var;
+ fb_info.blank = &xxxfb_blank;
+ /* This should give a reasonable default video mode */
+ fbgen_get_var(&disp.var, -1, &fb_info.gen);
+ fbgen_do_set_var(var, 1, &fbinfo.gen);
+ err = register_framebuffer(&fb_info.gen.info);
+ if (err < 0)
+ return err;
+ fbgen_set_disp(-1, &fb_info.gen.info);
+ fbgen_install_cmap(0, &fb_info.gen);
+ printk("fb%d: %s frame buffer device\n", GET_FB_IDX(fb_info.node),
+ fb_info.modename);
+
+ /* uncomment this if your driver cannot be unloaded */
+ /* MOD_INC_USE_COUNT; */
+
+ return mem_start;
+}
+
+
+ /*
+ * Cleanup
+ */
+
+void xxxfb_cleanup(struct fb_info *info)
+{
+ /*
+ * If your driver supports multiple boards, you should unregister and
+ * clean up all instances.
+ */
+
+ unregister_framebuffer(&fb_info);
+ /* ... */
+}
+
+
+ /*
+ * Setup
+ */
+
+__initfunc(void xxxfb_setup(char *options, int *ints))
+{
+ /* Parse user speficied options (`video=xxxfb:') */
+}
+
+
+/* ------------------------------------------------------------------------- */
+
+
+ /*
+ * Frame buffer operations
+ */
+
+static int xxxfb_open(const struct fb_info *info)
+{
+ /* Nothing, only a usage count for the moment */
+ MOD_INC_USE_COUNT;
+ return 0;
+}
+
+static int xxxfb_release(const struct fb_info *info)
+{
+ MOD_DEC_USE_COUNT;
+ return 0;
+}
+
+
+ /*
+ * In most cases the `generic' routines (fbgen_*) should be satisfactory.
+ * However, you're free to fill in your own replacements.
+ */
+
+static struct fb_ops xxxfb_ops = {
+ xxxfb_open, xxxfb_release, fbgen_get_fix, fbgen_get_var, fbgen_set_var,
+ fbgen_get_cmap, fbgen_set_cmap, fbgen_pan_display, NULL, fbgen_ioctl
+};
+
+
+/* ------------------------------------------------------------------------- */
+
+
+ /*
+ * Modularization
+ */
+
+#ifdef MODULE
+int init_module(void)
+{
+ return xxxfb_init(NULL);
+}
+
+void cleanup_module(void)
+{
+ xxxfb_cleanup(void);
+}
+#endif /* MODULE */
diff --git a/drivers/video/tgafb.c b/drivers/video/tgafb.c
index ac3746109..7e74f7449 100644
--- a/drivers/video/tgafb.c
+++ b/drivers/video/tgafb.c
@@ -17,13 +17,12 @@
*
* - How to set a single color register?
*
- * - We don't have support for CFB32 yet (fbcon-cfb32.c)
- *
* - Hardware cursor (useful for other graphics boards too)
*
* KNOWN PROBLEMS/TO DO ==================================================== */
+#include <linux/config.h>
#include <linux/module.h>
#include <linux/sched.h>
#include <linux/kernel.h>
@@ -37,11 +36,13 @@
#include <linux/interrupt.h>
#include <linux/fb.h>
#include <linux/init.h>
-#include <linux/bios32.h>
#include <linux/pci.h>
#include <linux/selection.h>
#include <asm/io.h>
+#include "fbcon-cfb8.h"
+#include "fbcon-cfb32.h"
+
/* TGA hardware description (minimal) */
/*
@@ -188,10 +189,17 @@ static unsigned int base_addr_presets[4] __initdata = {
unsigned char PLLbits[7] __initdata = { 0x80, 0x04, 0x00, 0x24, 0x44, 0x80, 0xb8 };
const unsigned long bt485_cursor_source[64] __initdata = {
+#if 1
+ 0x0000000000000000,0x0000000000000000,0x0000000000000000,0x0000000000000000,
+ 0x0000000000000000,0x0000000000000000,0x0000000000000000,0x0000000000000000,
+ 0x0000000000000000,0x0000000000000000,0x0000000000000000,0x0000000000000000,
+ 0x0000000000000000,0x0000000000000000,0x0000000000000000,0x0000000000000000,
+#else
0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,
0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,
0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,
0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,0x00000000000000ff,
+#endif
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
@@ -235,9 +243,8 @@ static int currcon = 0;
static struct display disp;
static struct fb_info fb_info;
static struct { u_char red, green, blue, pad; } palette[256];
-static char tgafb_name[16] = "DEC TGA ";
-static struct fb_fix_screeninfo fb_fix;
+static struct fb_fix_screeninfo fb_fix = { { "DEC TGA ", } };
static struct fb_var_screeninfo fb_var = { 0, };
@@ -245,18 +252,22 @@ static struct fb_var_screeninfo fb_var = { 0, };
* Interface used by the world
*/
-void tgafb_video_setup(char *options, int *ints);
-
-static int tgafb_open(int fbidx);
-static int tgafb_release(int fbidx);
-static int tgafb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int tgafb_get_var(struct fb_var_screeninfo *var, int con);
-static int tgafb_set_var(struct fb_var_screeninfo *var, int con);
-static int tgafb_pan_display(struct fb_var_screeninfo *var, int con);
-static int tgafb_get_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int tgafb_set_cmap(struct fb_cmap *cmap, int kspc, int con);
+static int tgafb_open(struct fb_info *info);
+static int tgafb_release(struct fb_info *info);
+static int tgafb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int tgafb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int tgafb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int tgafb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int tgafb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int tgafb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
static int tgafb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con);
+ u_long arg, int con, struct fb_info *info);
/*
@@ -264,10 +275,9 @@ static int tgafb_ioctl(struct inode *inode, struct file *file, u_int cmd,
*/
unsigned long tgafb_init(unsigned long mem_start);
-static int tgafbcon_switch(int con);
-static int tgafbcon_updatevar(int con);
-static void tgafbcon_blank(int blank);
-static int tgafbcon_setcmap(struct fb_cmap *cmap, int con);
+static int tgafbcon_switch(int con, struct fb_info *info);
+static int tgafbcon_updatevar(int con, struct fb_info *info);
+static void tgafbcon_blank(int blank, struct fb_info *info);
/*
@@ -275,18 +285,18 @@ static int tgafbcon_setcmap(struct fb_cmap *cmap, int con);
*/
static int tgafb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp);
+ u_int *transp, struct fb_info *info);
static int tgafb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp);
+ u_int transp, struct fb_info *info);
#if 1
static void tga_update_palette(void);
#endif
-static void do_install_cmap(int con);
+static void do_install_cmap(int con, struct fb_info *info);
static struct fb_ops tgafb_ops = {
tgafb_open, tgafb_release, tgafb_get_fix, tgafb_get_var, tgafb_set_var,
- tgafb_get_cmap, tgafb_set_cmap, tgafb_pan_display, tgafb_ioctl
+ tgafb_get_cmap, tgafb_set_cmap, tgafb_pan_display, NULL, tgafb_ioctl
};
@@ -294,7 +304,7 @@ static struct fb_ops tgafb_ops = {
* Open/Release the frame buffer device
*/
-static int tgafb_open(int fbidx)
+static int tgafb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -304,7 +314,7 @@ static int tgafb_open(int fbidx)
return(0);
}
-static int tgafb_release(int fbidx)
+static int tgafb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return(0);
@@ -315,7 +325,8 @@ static int tgafb_release(int fbidx)
* Get the Fixed Part of the Display
*/
-static int tgafb_get_fix(struct fb_fix_screeninfo *fix, int con)
+static int tgafb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
{
memcpy(fix, &fb_fix, sizeof(fb_fix));
return 0;
@@ -326,7 +337,8 @@ static int tgafb_get_fix(struct fb_fix_screeninfo *fix, int con)
* Get the User Defined Part of the Display
*/
-static int tgafb_get_var(struct fb_var_screeninfo *var, int con)
+static int tgafb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
memcpy(var, &fb_var, sizeof(fb_var));
return 0;
@@ -337,7 +349,8 @@ static int tgafb_get_var(struct fb_var_screeninfo *var, int con)
* Set the User Defined Part of the Display
*/
-static int tgafb_set_var(struct fb_var_screeninfo *var, int con)
+static int tgafb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
struct display *display;
int oldbpp = -1, err;
@@ -363,7 +376,7 @@ static int tgafb_set_var(struct fb_var_screeninfo *var, int con)
if (oldbpp != var->bits_per_pixel) {
if ((err = fb_alloc_cmap(&display->cmap, 0, 0)))
return err;
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
return 0;
}
@@ -375,7 +388,8 @@ static int tgafb_set_var(struct fb_var_screeninfo *var, int con)
* This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
*/
-static int tgafb_pan_display(struct fb_var_screeninfo *var, int con)
+static int tgafb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
if (var->xoffset || var->yoffset)
return -EINVAL;
@@ -387,14 +401,16 @@ static int tgafb_pan_display(struct fb_var_screeninfo *var, int con)
* Get the Colormap
*/
-static int tgafb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int tgafb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
if (con == currcon) /* current console? */
- return fb_get_cmap(cmap, &fb_display[con].var, kspc, tgafb_getcolreg);
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, tgafb_getcolreg,
+ info);
else if (fb_display[con].cmap.len) /* non default colormap? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return 0;
}
@@ -403,7 +419,8 @@ static int tgafb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
* Set the Colormap
*/
-static int tgafb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int tgafb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
int err;
@@ -413,7 +430,8 @@ static int tgafb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
return err;
}
if (con == currcon) { /* current console? */
- err = fb_set_cmap(cmap, &fb_display[con].var, kspc, tgafb_setcolreg);
+ err = fb_set_cmap(cmap, &fb_display[con].var, kspc, tgafb_setcolreg,
+ info);
#if 1
tga_update_palette();
#endif
@@ -425,7 +443,7 @@ static int tgafb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
static int tgafb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con)
+ u_long arg, int con, struct fb_info *info)
{
return -EINVAL;
}
@@ -437,22 +455,14 @@ static int tgafb_ioctl(struct inode *inode, struct file *file, u_int cmd,
__initfunc(unsigned long tgafb_init(unsigned long mem_start))
{
- unsigned char pci_bus, pci_devfn;
- int status;
int i, j, temp, err;
unsigned char *cbp;
+ struct pci_dev *pdev;
- status = pcibios_find_device (PCI_VENDOR_ID_DEC, PCI_DEVICE_ID_DEC_TGA,
- 0, &pci_bus, &pci_devfn);
- if (status == PCIBIOS_DEVICE_NOT_FOUND)
+ pdev = pci_find_device(PCI_VENDOR_ID_DEC, PCI_DEVICE_ID_DEC_TGA, NULL);
+ if (!pdev)
return mem_start;
-
- /*
- * read BASE_REG_0 for memory address
- */
- pcibios_read_config_dword(pci_bus, pci_devfn, PCI_BASE_ADDRESS_0,
- &tga_mem_base);
- tga_mem_base &= ~15;
+ tga_mem_base = pdev->base_address[0] & PCI_BASE_ADDRESS_MEM_MASK;
#ifdef DEBUG
printk("tgafb_init: mem_base 0x%x\n", tga_mem_base);
#endif /* DEBUG */
@@ -460,19 +470,18 @@ __initfunc(unsigned long tgafb_init(unsigned long mem_start))
tga_type = (readl((unsigned long)tga_mem_base) >> 12) & 0x0f;
switch (tga_type) {
case 0:
- strcat(tgafb_name, "8plane");
+ strcat(fb_fix.id, "8plane");
break;
case 1:
- strcat(tgafb_name, "24plane");
+ strcat(fb_fix.id, "24plane");
break;
case 3:
- strcat(tgafb_name, "24plusZ");
+ strcat(fb_fix.id, "24plusZ");
break;
default:
printk("TGA type (0x%x) unrecognized!\n", tga_type);
return mem_start;
}
- strcpy(fb_fix.id, tgafb_name);
tga_regs_base = ((unsigned long)tga_mem_base + TGA_REGS_OFFSET);
tga_fb_base = ((unsigned long)tga_mem_base + fb_offset_presets[tga_type]);
@@ -537,6 +546,9 @@ __initfunc(unsigned long tgafb_init(unsigned long mem_start))
TGA_WRITE_REG(default_red[j]|(BT485_DATA_PAL<<8), TGA_RAMDAC_REG);
TGA_WRITE_REG(default_grn[j]|(BT485_DATA_PAL<<8), TGA_RAMDAC_REG);
TGA_WRITE_REG(default_blu[j]|(BT485_DATA_PAL<<8), TGA_RAMDAC_REG);
+ palette[i].red=default_red[j];
+ palette[i].green=default_grn[j];
+ palette[i].blue=default_blu[j];
}
for (i = 0; i < 240*3; i += 4) {
TGA_WRITE_REG(0x55|(BT485_DATA_PAL<<8), TGA_RAMDAC_REG);
@@ -548,9 +560,9 @@ __initfunc(unsigned long tgafb_init(unsigned long mem_start))
/* initialize RAMDAC cursor colors */
BT485_WRITE(0, BT485_ADDR_CUR_WRITE);
- BT485_WRITE(0xaa, BT485_DATA_CUR); /* overscan WHITE */
- BT485_WRITE(0xaa, BT485_DATA_CUR); /* overscan WHITE */
- BT485_WRITE(0xaa, BT485_DATA_CUR); /* overscan WHITE */
+ BT485_WRITE(0x00, BT485_DATA_CUR); /* overscan WHITE */
+ BT485_WRITE(0x00, BT485_DATA_CUR); /* overscan WHITE */
+ BT485_WRITE(0x00, BT485_DATA_CUR); /* overscan WHITE */
BT485_WRITE(0x00, BT485_DATA_CUR); /* color 1 BLACK */
BT485_WRITE(0x00, BT485_DATA_CUR); /* color 1 BLACK */
@@ -677,7 +689,7 @@ __initfunc(unsigned long tgafb_init(unsigned long mem_start))
fb_var.xres = fb_var.xres_virtual = 640;
fb_var.yres = fb_var.yres_virtual = 480;
fb_fix.line_length = 80*fb_var.bits_per_pixel;
- fb_fix.smem_start = (char *)tga_fb_base;
+ fb_fix.smem_start = (char *)(tga_fb_base + LCA_DENSE_MEM);
fb_fix.smem_len = fb_fix.line_length*fb_var.yres;
fb_fix.type = FB_TYPE_PACKED_PIXELS;
fb_fix.type_aux = 0;
@@ -686,7 +698,16 @@ __initfunc(unsigned long tgafb_init(unsigned long mem_start))
fb_var.xoffset = fb_var.yoffset = 0;
fb_var.grayscale = 0;
- fb_var.red.offset = fb_var.green.offset = fb_var.blue.offset = 0;
+ if (tga_type == 0) { /* 8-plane */
+ fb_var.red.offset = 0;
+ fb_var.green.offset = 0;
+ fb_var.blue.offset = 0;
+ } else { /* 24-plane or 24plusZ */
+ /* XXX: is this correct?? */
+ fb_var.red.offset = 16;
+ fb_var.green.offset = 8;
+ fb_var.blue.offset = 0;
+ }
fb_var.red.length = fb_var.green.length = fb_var.blue.length = 8;
fb_var.red.msb_right = fb_var.green.msb_right = fb_var.blue.msb_right = 0;
fb_var.transp.offset = fb_var.transp.length = fb_var.transp.msb_right = 0;
@@ -717,41 +738,54 @@ __initfunc(unsigned long tgafb_init(unsigned long mem_start))
disp.line_length = fb_fix.line_length;
disp.can_soft_blank = 1;
disp.inverse = 0;
+ switch (tga_type) {
+#ifdef CONFIG_FBCON_CFB8
+ case 0: /* 8-plane */
+ disp.dispsw = &fbcon_cfb8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB32
+ case 1: /* 24-plane */
+ case 3: /* 24plusZ */
+ disp.dispsw = &fbcon_cfb32;
+ break;
+#endif
+ default:
+ disp.dispsw = NULL;
+ }
- strcpy(fb_info.modename, tgafb_name);
+ strcpy(fb_info.modename, fb_fix.id);
fb_info.node = -1;
fb_info.fbops = &tgafb_ops;
- fb_info.fbvar_num = 1;
- fb_info.fbvar = &fb_var;
fb_info.disp = &disp;
fb_info.fontname[0] = '\0';
fb_info.changevar = NULL;
fb_info.switch_con = &tgafbcon_switch;
fb_info.updatevar = &tgafbcon_updatevar;
fb_info.blank = &tgafbcon_blank;
- fb_info.setcmap = &tgafbcon_setcmap;
err = register_framebuffer(&fb_info);
if (err < 0)
return mem_start;
- tgafb_set_var(&fb_var, -1);
+ tgafb_set_var(&fb_var, -1, &fb_info);
- printk("%s frame buffer device\n", tgafb_name);
+ printk("fb%d: %s frame buffer device\n", GET_FB_IDX(fb_info.node),
+ fb_fix.id);
return mem_start;
}
-static int tgafbcon_switch(int con)
+static int tgafbcon_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
- tgafb_getcolreg);
+ tgafb_getcolreg, info);
currcon = con;
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return 0;
}
@@ -759,7 +793,7 @@ static int tgafbcon_switch(int con)
* Update the `var' structure (called by fbcon.c)
*/
-static int tgafbcon_updatevar(int con)
+static int tgafbcon_updatevar(int con, struct fb_info *info)
{
/* Nothing */
return 0;
@@ -769,28 +803,18 @@ static int tgafbcon_updatevar(int con)
* Blank the display.
*/
-static void tgafbcon_blank(int blank)
+static void tgafbcon_blank(int blank, struct fb_info *info)
{
/* Nothing */
}
/*
- * Set the colormap
- */
-
-static int tgafbcon_setcmap(struct fb_cmap *cmap, int con)
-{
- return(tgafb_set_cmap(cmap, 1, con));
-}
-
-
- /*
* Read a single color register and split it into
* colors/transparent. Return != 0 for invalid regno.
*/
static int tgafb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp)
+ u_int *transp, struct fb_info *info)
{
if (regno > 255)
return 1;
@@ -808,7 +832,7 @@ static int tgafb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
*/
static int tgafb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp)
+ u_int transp, struct fb_info *info)
{
if (regno > 255)
return 1;
@@ -816,6 +840,11 @@ static int tgafb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
palette[regno].green = green;
palette[regno].blue = blue;
+#ifdef CONFIG_FBCON_CFB32
+ if (regno < 16 && tga_type != 0)
+ fbcon_cfb32_cmap[regno] = (red << 16) | (green << 8) | blue;
+#endif /* CONFIG_FBCON_CFB32 */
+
/* How to set a single color register?? */
return 0;
@@ -853,22 +882,22 @@ static void tga_update_palette(void)
}
#endif
-static void do_install_cmap(int con)
+static void do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
- tgafb_setcolreg);
+ tgafb_setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
- &fb_display[con].var, 1, tgafb_setcolreg);
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, tgafb_setcolreg,
+ info);
#if 1
tga_update_palette();
#endif
}
-
#if 0 /* No cursor stuff yet */
/*
diff --git a/drivers/video/txtcon.c b/drivers/video/txtcon.c
index cdecc08b0..83165b49b 100644
--- a/drivers/video/txtcon.c
+++ b/drivers/video/txtcon.c
@@ -14,48 +14,55 @@
*/
+#include <linux/errno.h>
#include <linux/types.h>
+#include <linux/kdev_t.h>
#include <linux/console.h>
- /*
- * Interface used by the world
- */
+ /*
+ * Interface used by the world
+ */
-static int txtcon_startup(u_long *kmem_start, const char **display_desc);
+static unsigned long txtcon_startup(unsigned long kmem_start,
+ const char **display_desc);
static void txtcon_init(struct vc_data *conp);
-static int txtcon_deinit(struct vc_data *conp);
-static int txtcon_clear(struct vc_data *conp, int sy, int sx, int height,
- int width);
-static int txtcon_putc(struct vc_data *conp, int c, int y, int x);
-static int txtcon_putcs(struct vc_data *conp, const char *s, int count, int y,
- int x);
-static int txtcon_cursor(struct vc_data *conp, int mode);
-static int txtcon_scroll(struct vc_data *conp, int t, int b, int dir, int count);
-static int txtcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
- int height, int width);
+static void txtcon_deinit(struct vc_data *conp);
+static void txtcon_clear(struct vc_data *conp, int sy, int sx, int height,
+ int width);
+static void txtcon_putc(struct vc_data *conp, int c, int y, int x);
+static void txtcon_putcs(struct vc_data *conp, const char *s, int count, int y,
+ int x);
+static void txtcon_cursor(struct vc_data *conp, int mode);
+static void txtcon_scroll(struct vc_data *conp, int t, int b, int dir,
+ int count);
+static void txtcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
+ int height, int width);
static int txtcon_switch(struct vc_data *conp);
static int txtcon_blank(int blank);
static int txtcon_get_font(struct vc_data *conp, int *w, int *h, char *data);
static int txtcon_set_font(struct vc_data *conp, int w, int h, char *data);
static int txtcon_set_palette(struct vc_data *conp, unsigned char *table);
static int txtcon_scrolldelta(int lines);
+static int txtcon_set_mode(struct vc_data *conp, int mode);
-static int txtcon_startup(u_long *kmem_start, const char **display_desc)
+static unsigned long txtcon_startup(unsigned long kmem_start,
+ const char **display_desc)
{
- return -ENODEV;
+ return kmem_start;
}
static void txtcon_init(struct vc_data *conp)
{
+ /* ... */
}
-static int txtcon_deinit(struct vc_data *conp)
+static void txtcon_deinit(struct vc_data *conp)
{
- return 0;
+ /* ... */
}
@@ -64,90 +71,108 @@ static int txtcon_deinit(struct vc_data *conp)
/* txtcon_XXX routines - interface used by the world */
-static int txtcon_clear(struct vc_data *conp, int sy, int sx, int height,
- int width)
+static void txtcon_clear(struct vc_data *conp, int sy, int sx, int height,
+ int width)
{
- return -ENOSYS;
+ /* ... */
}
-static int txtcon_putc(struct vc_data *conp, int c, int y, int x)
+static void txtcon_putc(struct vc_data *conp, int c, int y, int x)
{
- return -ENOSYS;
+ /* ... */
}
-static int txtcon_putcs(struct vc_data *conp, const char *s, int count, int y,
- int x)
+static void txtcon_putcs(struct vc_data *conp, const char *s, int count, int y,
+ int x)
{
- return -ENOSYS;
+ /* ... */
}
-static int txtcon_cursor(struct vc_data *conp, int mode)
+static void txtcon_cursor(struct vc_data *conp, int mode)
{
- return -ENOSYS;
+ /* ... */
}
-static int txtcon_scroll(struct vc_data *conp, int t, int b, int dir, int count)
+static void txtcon_scroll(struct vc_data *conp, int t, int b, int dir,
+ int count)
{
- return -ENOSYS;
+ /* ... */
}
-static int txtcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
- int height, int width)
+static void txtcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
+ int height, int width)
{
- return -ENOSYS;
+ /* ... */
}
static int txtcon_switch(struct vc_data *conp)
{
- return -ENOSYS;
+ return -ENOSYS;
}
static int txtcon_blank(int blank)
{
- return -ENOSYS;
+ return -ENOSYS;
}
static int txtcon_get_font(struct vc_data *conp, int *w, int *h, char *data)
{
- return -ENOSYS;
+ return -ENOSYS;
}
static int txtcon_set_font(struct vc_data *conp, int w, int h, char *data)
{
- return -ENOSYS;
+ return -ENOSYS;
}
static int txtcon_set_palette(struct vc_data *conp, unsigned char *table)
{
- return -ENOSYS;
+ return -ENOSYS;
}
static int txtcon_scrolldelta(int lines)
{
- return -ENOSYS;
+ return -ENOSYS;
+}
+
+static int txtcon_set_mode(struct vc_data *conp, int mode)
+{
+ return -ENOSYS;
}
/* ====================================================================== */
- /*
- * The console `switch' structure for the text mode based console
- */
+ /*
+ * The console `switch' structure for the text mode based console
+ */
struct consw txt_con = {
- txtcon_startup, txtcon_init, txtcon_deinit, txtcon_clear, txtcon_putc,
- txtcon_putcs, txtcon_cursor, txtcon_scroll, txtcon_bmove, txtcon_switch,
- txtcon_blank, txtcon_get_font, txtcon_set_font, txtcon_set_palette,
- txtcon_scrolldelta
+ txtcon_startup,
+ txtcon_init,
+ txtcon_deinit,
+ txtcon_clear,
+ txtcon_putc,
+ txtcon_putcs,
+ txtcon_cursor,
+ txtcon_scroll,
+ txtcon_bmove,
+ txtcon_switch,
+ txtcon_blank,
+ txtcon_get_font,
+ txtcon_set_font,
+ txtcon_set_palette,
+ txtcon_scrolldelta,
+ txtcon_set_mode
};
diff --git a/drivers/video/vfb.c b/drivers/video/vfb.c
index 63e7f7ca2..eea430ffa 100644
--- a/drivers/video/vfb.c
+++ b/drivers/video/vfb.c
@@ -8,6 +8,7 @@
* more details.
*/
+#include <linux/config.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
@@ -22,6 +23,14 @@
#include <linux/fb.h>
#include <linux/init.h>
+#include "fbcon-mfb.h"
+#include "fbcon-cfb2.h"
+#include "fbcon-cfb4.h"
+#include "fbcon-cfb8.h"
+#include "fbcon-cfb16.h"
+#include "fbcon-cfb24.h"
+#include "fbcon-cfb32.h"
+
#define arraysize(x) (sizeof(x)/sizeof(*(x)))
@@ -41,61 +50,51 @@ static int currcon = 0;
static struct display disp;
static struct fb_info fb_info;
static struct { u_char red, green, blue, pad; } palette[256];
-static char virtual_fb_name[16] = "Virtual FB";
-
-static struct fb_var_screeninfo virtual_fb_predefined[] = {
-
- /*
- * Autodetect (Default) Video Mode
- */
-
- {
- /* 640x480, 8 bpp */
- 640, 480, 640, 480, 0, 0, 8, 0,
- {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
- 0, 0, -1, -1, FB_ACCEL_NONE, 20000, 64, 64, 32, 32, 64, 2,
- 0, FB_VMODE_NONINTERLACED
- },
-
- /*
- * User Defined Video Modes (8)
- */
-
- { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }, { 0, }
+static char vfb_name[16] = "Virtual FB";
+
+static struct fb_var_screeninfo vfb_default = {
+ /* 640x480, 8 bpp */
+ 640, 480, 640, 480, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, 20000, 64, 64, 32, 32, 64, 2,
+ 0, FB_VMODE_NONINTERLACED
};
-#define NUM_USER_MODES (8)
-#define NUM_TOTAL_MODES arraysize(virtual_fb_predefined)
-#define NUM_PREDEF_MODES (1)
+static int vfb_enable = 0; /* disabled by default */
/*
* Interface used by the world
*/
-void vfb_video_setup(char *options, int *ints);
-
-static int virtual_fb_open(int fbidx);
-static int virtual_fb_release(int fbidx);
-static int virtual_fb_get_fix(struct fb_fix_screeninfo *fix, int con);
-static int virtual_fb_get_var(struct fb_var_screeninfo *var, int con);
-static int virtual_fb_set_var(struct fb_var_screeninfo *var, int con);
-static int virtual_fb_pan_display(struct fb_var_screeninfo *var, int con);
-static int virtual_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int virtual_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con);
-static int virtual_fb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con);
+void vfb_setup(char *options, int *ints);
+
+static int vfb_open(struct fb_info *info);
+static int vfb_release(struct fb_info *info);
+static int vfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info);
+static int vfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int vfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int vfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int vfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int vfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int vfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info);
/*
* Interface to the low level console driver
*/
-unsigned long virtual_fb_init(unsigned long mem_start);
-static int vfbcon_switch(int con);
-static int vfbcon_updatevar(int con);
-static void vfbcon_blank(int blank);
-static int vfbcon_setcmap(struct fb_cmap *cmap, int con);
+unsigned long vfb_init(unsigned long mem_start);
+static int vfbcon_switch(int con, struct fb_info *info);
+static int vfbcon_updatevar(int con, struct fb_info *info);
+static void vfbcon_blank(int blank, struct fb_info *info);
/*
@@ -107,16 +106,15 @@ static void vfb_encode_fix(struct fb_fix_screeninfo *fix,
struct fb_var_screeninfo *var);
static void set_color_bitfields(struct fb_var_screeninfo *var);
static int vfb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp);
+ u_int *transp, struct fb_info *info);
static int vfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp);
-static void do_install_cmap(int con);
+ u_int transp, struct fb_info *info);
+static void do_install_cmap(int con, struct fb_info *info);
-static struct fb_ops virtual_fb_ops = {
- virtual_fb_open, virtual_fb_release, virtual_fb_get_fix,
- virtual_fb_get_var, virtual_fb_set_var, virtual_fb_get_cmap,
- virtual_fb_set_cmap, virtual_fb_pan_display, virtual_fb_ioctl
+static struct fb_ops vfb_ops = {
+ vfb_open, vfb_release, vfb_get_fix, vfb_get_var, vfb_set_var, vfb_get_cmap,
+ vfb_set_cmap, vfb_pan_display, NULL, vfb_ioctl
};
@@ -124,7 +122,7 @@ static struct fb_ops virtual_fb_ops = {
* Open/Release the frame buffer device
*/
-static int virtual_fb_open(int fbidx)
+static int vfb_open(struct fb_info *info)
{
/*
* Nothing, only a usage count for the moment
@@ -134,7 +132,7 @@ static int virtual_fb_open(int fbidx)
return(0);
}
-static int virtual_fb_release(int fbidx)
+static int vfb_release(struct fb_info *info)
{
MOD_DEC_USE_COUNT;
return(0);
@@ -145,12 +143,13 @@ static int virtual_fb_release(int fbidx)
* Get the Fixed Part of the Display
*/
-static int virtual_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
+static int vfb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
{
struct fb_var_screeninfo *var;
if (con == -1)
- var = &virtual_fb_predefined[0];
+ var = &vfb_default;
else
var = &fb_display[con].var;
vfb_encode_fix(fix, var);
@@ -162,10 +161,11 @@ static int virtual_fb_get_fix(struct fb_fix_screeninfo *fix, int con)
* Get the User Defined Part of the Display
*/
-static int virtual_fb_get_var(struct fb_var_screeninfo *var, int con)
+static int vfb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
if (con == -1)
- *var = virtual_fb_predefined[0];
+ *var = vfb_default;
else
*var = fb_display[con].var;
set_color_bitfields(var);
@@ -177,7 +177,8 @@ static int virtual_fb_get_var(struct fb_var_screeninfo *var, int con)
* Set the User Defined Part of the Display
*/
-static int virtual_fb_set_var(struct fb_var_screeninfo *var, int con)
+static int vfb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
int err, activate = var->activate;
int oldxres, oldyres, oldvxres, oldvyres, oldbpp;
@@ -258,13 +259,53 @@ static int virtual_fb_set_var(struct fb_var_screeninfo *var, int con)
display->line_length = fix.line_length;
display->can_soft_blank = 1;
display->inverse = 0;
+ switch (var->bits_per_pixel) {
+#ifdef CONFIG_FBCON_MFB
+ case 1:
+ display->dispsw = &fbcon_mfb;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB2
+ case 2:
+ display->dispsw = &fbcon_cfb2;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB4
+ case 4:
+ display->dispsw = &fbcon_cfb4;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_cfb8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ case 16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB24
+ case 24:
+ display->dispsw = &fbcon_cfb24;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB32
+ case 32:
+ display->dispsw = &fbcon_cfb32;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ break;
+ }
if (fb_info.changevar)
(*fb_info.changevar)(con);
}
if (oldbpp != var->bits_per_pixel) {
if ((err = fb_alloc_cmap(&display->cmap, 0, 0)))
return err;
- do_install_cmap(con);
+ do_install_cmap(con, info);
}
}
return 0;
@@ -277,7 +318,8 @@ static int virtual_fb_set_var(struct fb_var_screeninfo *var, int con)
* This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
*/
-static int virtual_fb_pan_display(struct fb_var_screeninfo *var, int con)
+static int vfb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
{
if (var->vmode & FB_VMODE_YWRAP) {
if (var->yoffset < 0 ||
@@ -304,14 +346,16 @@ static int virtual_fb_pan_display(struct fb_var_screeninfo *var, int con)
* Get the Colormap
*/
-static int virtual_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int vfb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
if (con == currcon) /* current console? */
- return fb_get_cmap(cmap, &fb_display[con].var, kspc, vfb_getcolreg);
+ return fb_get_cmap(cmap, &fb_display[con].var, kspc, vfb_getcolreg,
+ info);
else if (fb_display[con].cmap.len) /* non default colormap? */
fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
else
- fb_copy_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
cmap, kspc ? 0 : 2);
return 0;
}
@@ -320,7 +364,8 @@ static int virtual_fb_get_cmap(struct fb_cmap *cmap, int kspc, int con)
* Set the Colormap
*/
-static int virtual_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
+static int vfb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
{
int err;
@@ -330,7 +375,8 @@ static int virtual_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
return err;
}
if (con == currcon) /* current console? */
- return fb_set_cmap(cmap, &fb_display[con].var, kspc, vfb_setcolreg);
+ return fb_set_cmap(cmap, &fb_display[con].var, kspc, vfb_setcolreg,
+ info);
else
fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
return 0;
@@ -341,19 +387,21 @@ static int virtual_fb_set_cmap(struct fb_cmap *cmap, int kspc, int con)
* Virtual Frame Buffer Specific ioctls
*/
-static int virtual_fb_ioctl(struct inode *inode, struct file *file, u_int cmd,
- u_long arg, int con)
+static int vfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info)
{
return -EINVAL;
}
-__initfunc(void vfb_video_setup(char *options, int *ints))
+__initfunc(void vfb_setup(char *options, int *ints))
{
char *this_opt;
fb_info.fontname[0] = '\0';
+ vfb_enable = 1;
+
if (!options || !*options)
return;
@@ -369,10 +417,13 @@ __initfunc(void vfb_video_setup(char *options, int *ints))
* Initialisation
*/
-__initfunc(unsigned long virtual_fb_init(unsigned long mem_start))
+__initfunc(unsigned long vfb_init(unsigned long mem_start))
{
int err;
+ if (!vfb_enable)
+ return mem_start;
+
if (mem_start) {
videomemory = mem_start;
mem_start += videomemorysize;
@@ -382,40 +433,37 @@ __initfunc(unsigned long virtual_fb_init(unsigned long mem_start))
if (!videomemory)
return mem_start;
- strcpy(fb_info.modename, virtual_fb_name);
+ strcpy(fb_info.modename, vfb_name);
fb_info.changevar = NULL;
fb_info.node = -1;
- fb_info.fbops = &virtual_fb_ops;
- fb_info.fbvar_num = NUM_TOTAL_MODES;
- fb_info.fbvar = virtual_fb_predefined;
+ fb_info.fbops = &vfb_ops;
fb_info.disp = &disp;
fb_info.switch_con = &vfbcon_switch;
fb_info.updatevar = &vfbcon_updatevar;
fb_info.blank = &vfbcon_blank;
- fb_info.setcmap = &vfbcon_setcmap;
err = register_framebuffer(&fb_info);
if (err < 0)
return mem_start;
- virtual_fb_set_var(&virtual_fb_predefined[0], -1);
+ vfb_set_var(&vfb_default, -1, &fb_info);
- printk("Virtual frame buffer device, using %ldK of video memory\n",
- videomemorysize>>10);
+ printk("fb%d: Virtual frame buffer device, using %ldK of video memory\n",
+ GET_FB_IDX(fb_info.node), videomemorysize>>10);
return mem_start;
}
-static int vfbcon_switch(int con)
+static int vfbcon_switch(int con, struct fb_info *info)
{
/* Do we have to save the colormap? */
if (fb_display[currcon].cmap.len)
fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
- vfb_getcolreg);
+ vfb_getcolreg, info);
currcon = con;
/* Install new colormap */
- do_install_cmap(con);
+ do_install_cmap(con, info);
return 0;
}
@@ -423,7 +471,7 @@ static int vfbcon_switch(int con)
* Update the `var' structure (called by fbcon.c)
*/
-static int vfbcon_updatevar(int con)
+static int vfbcon_updatevar(int con, struct fb_info *info)
{
/* Nothing */
return 0;
@@ -433,21 +481,11 @@ static int vfbcon_updatevar(int con)
* Blank the display.
*/
-static void vfbcon_blank(int blank)
+static void vfbcon_blank(int blank, struct fb_info *info)
{
/* Nothing */
}
- /*
- * Set the colormap
- */
-
-static int vfbcon_setcmap(struct fb_cmap *cmap, int con)
-{
- return(virtual_fb_set_cmap(cmap, 1, con));
-}
-
-
static u_long get_line_length(int xres_virtual, int bpp)
{
u_long length;
@@ -462,7 +500,7 @@ static void vfb_encode_fix(struct fb_fix_screeninfo *fix,
struct fb_var_screeninfo *var)
{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
- strcpy(fix->id, virtual_fb_name);
+ strcpy(fix->id, vfb_name);
fix->smem_start = (caddr_t)videomemory;
fix->smem_len = videomemorysize;
fix->type = FB_TYPE_PACKED_PIXELS;
@@ -471,6 +509,8 @@ static void vfb_encode_fix(struct fb_fix_screeninfo *fix,
case 1:
fix->visual = FB_VISUAL_MONO01;
break;
+ case 2:
+ case 4:
case 8:
fix->visual = FB_VISUAL_PSEUDOCOLOR;
break;
@@ -544,7 +584,7 @@ static void set_color_bitfields(struct fb_var_screeninfo *var)
*/
static int vfb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
- u_int *transp)
+ u_int *transp, struct fb_info *info)
{
if (regno > 255)
return 1;
@@ -562,7 +602,7 @@ static int vfb_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
*/
static int vfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
- u_int transp)
+ u_int transp, struct fb_info *info)
{
if (regno > 255)
return 1;
@@ -573,23 +613,23 @@ static int vfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
}
-static void do_install_cmap(int con)
+static void do_install_cmap(int con, struct fb_info *info)
{
if (con != currcon)
return;
if (fb_display[con].cmap.len)
fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
- vfb_setcolreg);
+ vfb_setcolreg, info);
else
- fb_set_cmap(fb_default_cmap(fb_display[con].var.bits_per_pixel),
- &fb_display[con].var, 1, vfb_setcolreg);
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, vfb_setcolreg, info);
}
#ifdef MODULE
int init_module(void)
{
- return(virtual_fb_init(NULL));
+ return(vfb_init(NULL));
}
void cleanup_module(void)
diff --git a/drivers/video/vgacon.c b/drivers/video/vgacon.c
index 83a908a09..623ea799d 100644
--- a/drivers/video/vgacon.c
+++ b/drivers/video/vgacon.c
@@ -87,16 +87,16 @@
static unsigned long vgacon_startup(unsigned long kmem_start,
const char **display_desc);
static void vgacon_init(struct vc_data *conp);
-static int vgacon_deinit(struct vc_data *conp);
-static int vgacon_clear(struct vc_data *conp, int sy, int sx, int height,
- int width);
-static int vgacon_putc(struct vc_data *conp, int c, int ypos, int xpos);
-static int vgacon_putcs(struct vc_data *conp, const char *s, int count,
- int ypos, int xpos);
-static int vgacon_cursor(struct vc_data *conp, int mode);
-static int vgacon_scroll(struct vc_data *conp, int t, int b,
- int dir, int count);
-static int vgacon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
+static void vgacon_deinit(struct vc_data *conp);
+static void vgacon_clear(struct vc_data *conp, int sy, int sx, int height,
+ int width);
+static void vgacon_putc(struct vc_data *conp, int c, int ypos, int xpos);
+static void vgacon_putcs(struct vc_data *conp, const char *s, int count,
+ int ypos, int xpos);
+static void vgacon_cursor(struct vc_data *conp, int mode);
+static void vgacon_scroll(struct vc_data *conp, int t, int b, int dir,
+ int count);
+static void vgacon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
int height, int width);
static int vgacon_switch(struct vc_data *conp);
static int vgacon_blank(int blank);
@@ -104,6 +104,7 @@ static int vgacon_get_font(struct vc_data *conp, int *w, int *h, char *data);
static int vgacon_set_font(struct vc_data *conp, int w, int h, char *data);
static int vgacon_set_palette(struct vc_data *conp, unsigned char *table);
static int vgacon_scrolldelta(int lines);
+static int vgacon_set_mode(struct vc_data *conp, int mode);
/*
@@ -215,25 +216,6 @@ __initfunc(static unsigned long vgacon_startup(unsigned long kmem_start,
unsigned short saved;
unsigned short *p;
- /*
- * Find out if there is a graphics card present.
- * Are there smarter methods around?
- */
- p = (unsigned short *)(((ORIG_VIDEO_MODE == 7) ? 0xb0000 : 0xb8000) +
- + VGA_OFFSET);
- saved = vga_readw(p);
- vga_writew(0xAA55, p);
- if (vga_readw(p) != 0xAA55) {
- vga_writew(saved, p);
- return kmem_start;
- }
- vga_writew(0x55AA, p);
- if (vga_readw(p) != 0x55AA) {
- vga_writew(saved, p);
- return kmem_start;
- }
- vga_writew(saved, p);
-
vga_video_num_lines = ORIG_VIDEO_LINES;
vga_video_num_columns = ORIG_VIDEO_COLS;
vga_video_size_row = 2 * ORIG_VIDEO_COLS;
@@ -327,6 +309,24 @@ __initfunc(static unsigned long vgacon_startup(unsigned long kmem_start,
}
}
+ /*
+ * Find out if there is a graphics card present.
+ * Are there smarter methods around?
+ */
+ p = (unsigned short *)vga_video_mem_base;
+ saved = vga_readw(p);
+ vga_writew(0xAA55, p);
+ if (vga_readw(p) != 0xAA55) {
+ vga_writew(saved, p);
+ return kmem_start;
+ }
+ vga_writew(0x55AA, p);
+ if (vga_readw(p) != 0x55AA) {
+ vga_writew(saved, p);
+ return kmem_start;
+ }
+ vga_writew(saved, p);
+
vga_hardscroll_enabled = (vga_hardscroll_disabled_by_init ? 0 :
(vga_video_type == VIDEO_TYPE_EGAC
|| vga_video_type == VIDEO_TYPE_VGAC
@@ -358,22 +358,21 @@ static void vgacon_init(struct vc_data *conp)
conp->vc_can_do_color = vga_can_do_color;
}
-static int vgacon_deinit(struct vc_data *conp)
+static void vgacon_deinit(struct vc_data *conp)
{
- return 0;
}
/* ====================================================================== */
-static int vgacon_clear(struct vc_data *conp, int sy, int sx, int height,
- int width)
+static void vgacon_clear(struct vc_data *conp, int sy, int sx, int height,
+ int width)
{
int rows;
unsigned long dest;
if (console_blanked)
- return 0;
+ return;
dest = vga_video_mem_base + sy*vga_video_size_row + sx*2;
if (sx == 0 && width == vga_video_num_columns)
@@ -381,41 +380,38 @@ static int vgacon_clear(struct vc_data *conp, int sy, int sx, int height,
else
for (rows = height; rows-- ; dest += vga_video_size_row)
vga_memsetw((void *)dest, conp->vc_video_erase_char, width);
- return 0;
}
-static int vgacon_putc(struct vc_data *conp, int c, int ypos, int xpos)
+static void vgacon_putc(struct vc_data *conp, int c, int ypos, int xpos)
{
- u_short *p;
+ u16 *p;
if (console_blanked)
- return 0;
+ return;
- p = (u_short *)(vga_video_mem_base+ypos*vga_video_size_row+xpos*2);
+ p = (u16 *)(vga_video_mem_base+ypos*vga_video_size_row+xpos*2);
vga_writew(conp->vc_attr << 8 | c, p);
- return 0;
}
-static int vgacon_putcs(struct vc_data *conp, const char *s, int count,
- int ypos, int xpos)
+static void vgacon_putcs(struct vc_data *conp, const char *s, int count,
+ int ypos, int xpos)
{
- u_short *p;
- u_short sattr;
+ u16 *p;
+ u16 sattr;
if (console_blanked)
- return 0;
+ return;
- p = (u_short *)(vga_video_mem_base+ypos*vga_video_size_row+xpos*2);
+ p = (u16 *)(vga_video_mem_base+ypos*vga_video_size_row+xpos*2);
sattr = conp->vc_attr << 8;
while (count--)
vga_writew(sattr | *s++, p++);
- return 0;
}
-static int vgacon_cursor(struct vc_data *conp, int mode)
+static void vgacon_cursor(struct vc_data *conp, int mode)
{
switch (mode) {
case CM_ERASE:
@@ -427,14 +423,14 @@ static int vgacon_cursor(struct vc_data *conp, int mode)
write_vga(14, conp->vc_y*vga_video_num_columns+conp->vc_x);
break;
}
- return 0;
}
-static int vgacon_scroll(struct vc_data *conp, int t, int b, int dir, int count)
+static void vgacon_scroll(struct vc_data *conp, int t, int b, int dir,
+ int count)
{
if (console_blanked)
- return 0;
+ return;
vgacon_cursor(conp, CM_ERASE);
@@ -469,19 +465,17 @@ static int vgacon_scroll(struct vc_data *conp, int t, int b, int dir, int count)
vgacon_clear(conp, 0, t, conp->vc_rows, count);
break;
}
-
- return 0;
}
-static int vgacon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
- int height, int width)
+static void vgacon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
+ int height, int width)
{
unsigned long src, dst;
int rows;
if (console_blanked)
- return 0;
+ return;
if (sx == 0 && dx == 0 && width == vga_video_num_columns) {
src = vga_video_mem_base + sy * vga_video_size_row;
@@ -505,7 +499,6 @@ static int vgacon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
dst -= vga_video_size_row;
}
}
- return 0;
}
@@ -522,7 +515,7 @@ static int vgacon_blank(int blank)
return 0;
} else {
/* Tell console.c that it has to restore the screen itself */
- return(1);
+ return 1;
}
return 0;
}
@@ -564,6 +557,11 @@ static int vgacon_scrolldelta(int lines)
return -ENOSYS;
}
+static int vgacon_set_mode(struct vc_data *conp, int mode)
+{
+ return -ENOSYS;
+}
+
__initfunc(static int vgacon_show_logo( void ))
{
@@ -587,5 +585,5 @@ struct consw vga_con = {
vgacon_startup, vgacon_init, vgacon_deinit, vgacon_clear, vgacon_putc,
vgacon_putcs, vgacon_cursor, vgacon_scroll, vgacon_bmove, vgacon_switch,
vgacon_blank, vgacon_get_font, vgacon_set_font, vgacon_set_palette,
- vgacon_scrolldelta
+ vgacon_scrolldelta, vgacon_set_mode
};
diff --git a/drivers/video/virgefb.c b/drivers/video/virgefb.c
new file mode 100644
index 000000000..d08e4a722
--- /dev/null
+++ b/drivers/video/virgefb.c
@@ -0,0 +1,1190 @@
+/*
+ * linux/drivers/video/virgefb.c -- CyberVision64/3D frame buffer device
+ *
+ * Copyright (C) 1997 André Heynatz
+ *
+ *
+ * This file is based on the CyberVision frame buffer device (cyberfb.c):
+ *
+ * Copyright (C) 1996 Martin Apel
+ * Geert Uytterhoeven
+ *
+ * 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.
+ */
+
+#undef VIRGEFBDEBUG
+
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/string.h>
+#include <linux/mm.h>
+#include <linux/tty.h>
+#include <linux/malloc.h>
+#include <linux/delay.h>
+#include <linux/zorro.h>
+#include <linux/fb.h>
+#include <linux/init.h>
+#include <asm/uaccess.h>
+#include <asm/system.h>
+#include <asm/irq.h>
+#include <asm/pgtable.h>
+#include <asm/amigahw.h>
+
+#include "s3blit.h"
+#include "fbcon.h"
+#include "fbcon-cfb8.h"
+#include "fbcon-cfb16.h"
+
+
+#ifdef VIRGEFBDEBUG
+#define DPRINTK(fmt, args...) printk(KERN_DEBUG "%s: " fmt, __FUNCTION__ , ## args)
+#else
+#define DPRINTK(fmt, args...)
+#endif
+
+#define arraysize(x) (sizeof(x)/sizeof(*(x)))
+
+#if 1
+#define vgawb_3d(reg,dat) \
+ (*((unsigned char *)(CyberVGARegs + (reg ^ 3))) = dat)
+#define vgaww_3d(reg,dat) \
+ (*((unsigned word *)(CyberVGARegs + (reg ^ 2))) = swab16(dat))
+#define vgawl_3d(reg,dat) \
+ (*((unsigned long *)(CyberVGARegs + reg)) = swab32(dat))
+#else
+ /*
+ * Dunno why this doesn't work at the moment - we'll have to look at
+ * it later.
+ */
+#define vgawb_3d(reg,dat) \
+ (*((unsigned char *)(CyberRegs + 0x8000 + reg)) = dat)
+#define vgaww_3d(reg,dat) \
+ (*((unsigned word *)(CyberRegs + 0x8000 + reg)) = dat)
+#define vgawl_3d(reg,dat) \
+ (*((unsigned long *)(CyberRegs + 0x8000 + reg)) = dat)
+#endif
+
+ /*
+ * We asume P5 mapped the big-endian version of these registers.
+ */
+#define wb_3d(reg,dat) \
+ (*((unsigned char volatile *)(CyberRegs + reg)) = dat)
+#define ww_3d(reg,dat) \
+ (*((unsigned word volatile *)(CyberRegs + reg)) = dat)
+#define wl_3d(reg,dat) \
+ (*((unsigned long volatile *)(CyberRegs + reg)) = dat)
+
+#define rl_3d(reg) \
+ (*((unsigned long volatile *)(CyberRegs + reg)))
+
+
+
+
+
+
+struct virgefb_par {
+ int xres;
+ int yres;
+ int bpp;
+};
+
+static struct virgefb_par current_par;
+
+static int current_par_valid = 0;
+static int currcon = 0;
+
+static struct display disp;
+static struct fb_info fb_info;
+
+
+/*
+ * Switch for Chipset Independency
+ */
+
+static struct fb_hwswitch {
+
+ /* Initialisation */
+
+ int (*init)(void);
+
+ /* Display Control */
+
+ int (*encode_fix)(struct fb_fix_screeninfo *fix, struct virgefb_par *par);
+ int (*decode_var)(struct fb_var_screeninfo *var, struct virgefb_par *par);
+ int (*encode_var)(struct fb_var_screeninfo *var, struct virgefb_par *par);
+ int (*getcolreg)(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info);
+ int (*setcolreg)(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info);
+ void (*blank)(int blank);
+} *fbhw;
+
+
+/*
+ * Frame Buffer Name
+ */
+
+static char virgefb_name[16] = "Cybervision/3D";
+
+
+/*
+ * Cybervision Graphics Board
+ */
+
+#define VIRGE8_WIDTH 1152
+#define VIRGE8_HEIGHT 886
+#define VIRGE8_PIXCLOCK 12500 /* ++Geert: Just a guess */
+
+#if 0
+#define VIRGE16_WIDTH 800
+#define VIRGE16_HEIGHT 600
+#endif
+#define VIRGE16_PIXCLOCK 25000 /* ++Geert: Just a guess */
+
+
+static unsigned int CyberKey = 0;
+static unsigned char Cyber_colour_table [256][4];
+static unsigned long CyberMem;
+static unsigned long CyberSize;
+static volatile char *CyberRegs;
+static volatile unsigned long CyberVGARegs; /* ++Andre: for CV64/3D, see macros at the beginning */
+
+
+/*
+ * Predefined Video Modes
+ */
+
+static struct fb_videomode virgefb_predefined[] __initdata = {
+ {
+ "640x480-8", { /* Cybervision 8 bpp */
+ 640, 480, 640, 480, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "800x600-8", { /* Cybervision 8 bpp */
+ 800, 600, 800, 600, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1024x768-8", { /* Cybervision 8 bpp */
+ 1024, 768, 1024, 768, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1152x886-8", { /* Cybervision 8 bpp */
+ 1152, 886, 1152, 886, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1280x1024-8", { /* Cybervision 8 bpp */
+ 1280, 1024, 1280, 1024, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "1600x1200-8", { /* Cybervision 8 bpp */
+ 1600, 1200, 1600, 1200, 0, 0, 8, 0,
+ {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE8_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }, {
+ "800x600-16", { /* Cybervision 16 bpp */
+ 800, 600, 800, 600, 0, 0, 16, 0,
+ {11, 5, 0}, {5, 6, 0}, {0, 5, 0}, {0, 0, 0},
+ 0, 0, -1, -1, FB_ACCEL_NONE, VIRGE16_PIXCLOCK, 64, 96, 35, 12, 112, 2,
+ FB_SYNC_COMP_HIGH_ACT|FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED
+ }
+ }
+};
+
+
+#define NUM_TOTAL_MODES arraysize(virgefb_predefined)
+
+
+static int Cyberfb_inverse = 0;
+#if 0
+static int Cyberfb_Cyber8 = 0; /* Use Cybervision board */
+static int Cyberfb_Cyber16 = 0; /* Use Cybervision board */
+#endif
+
+/*
+ * Some default modes
+ */
+
+#define VIRGE8_DEFMODE (0)
+#define VIRGE16_DEFMODE (6)
+
+static struct fb_var_screeninfo virgefb_default;
+
+
+/*
+ * Interface used by the world
+ */
+
+void virgefb_setup(char *options, int *ints);
+
+static int virgefb_open(struct fb_info *info);
+static int virgefb_release(struct fb_info *info);
+static int virgefb_get_fix(struct fb_fix_screeninfo *fix, int con, struct
+fb_info *info);
+static int virgefb_get_var(struct fb_var_screeninfo *var, int con, struct
+fb_info *info);
+static int virgefb_set_var(struct fb_var_screeninfo *var, int con, struct
+fb_info *info);
+static int virgefb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int virgefb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info);
+static int virgefb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info);
+static int virgefb_ioctl(struct inode *inode, struct file *file, u_int cmd,
+ u_long arg, int con, struct fb_info *info);
+
+
+/*
+ * Interface to the low level console driver
+ */
+
+unsigned long virgefb_init(unsigned long mem_start);
+static int Cyberfb_switch(int con, struct fb_info *info);
+static int Cyberfb_updatevar(int con, struct fb_info *info);
+static void Cyberfb_blank(int blank, struct fb_info *info);
+
+
+/*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static struct display_switch fbcon_virge8;
+#endif
+
+
+/*
+ * Hardware Specific Routines
+ */
+
+static int Cyber_init(void);
+static int Cyber_encode_fix(struct fb_fix_screeninfo *fix,
+ struct virgefb_par *par);
+static int Cyber_decode_var(struct fb_var_screeninfo *var,
+ struct virgefb_par *par);
+static int Cyber_encode_var(struct fb_var_screeninfo *var,
+ struct virgefb_par *par);
+static int Cyber_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info);
+static int Cyber_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info);
+static void Cyber_blank(int blank);
+
+
+/*
+ * Internal routines
+ */
+
+static void virgefb_get_par(struct virgefb_par *par);
+static void virgefb_set_par(struct virgefb_par *par);
+static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive);
+static void do_install_cmap(int con, struct fb_info *info);
+static void virgefb_set_disp(int con, struct fb_info *info);
+static int get_video_mode(const char *name);
+
+
+/* -------------------- Hardware specific routines ------------------------- */
+
+
+/*
+ * Initialization
+ *
+ * Set the default video mode for this chipset. If a video mode was
+ * specified on the command line, it will override the default mode.
+ */
+
+static int Cyber_init(void)
+{
+ int i;
+
+ for (i = 0; i < 256; i++)
+ {
+ Cyber_colour_table [i][0] = i;
+ Cyber_colour_table [i][1] = i;
+ Cyber_colour_table [i][2] = i;
+ Cyber_colour_table [i][3] = 0;
+ }
+
+ /*
+ * Just clear the thing for the biggest mode.
+ *
+ * ++Andre, TODO: determine size first, then clear all memory
+ * (the 3D penguin might need texture memory :-) )
+ */
+
+ memset ((char*)CyberMem, 0, 1600 * 1200);
+
+ /* Disable hardware cursor */
+ CyberSize = 0x00400000; /* 4 MB */
+
+ vgawb_3d(0x3c8, 255);
+ vgawb_3d(0x3c9, 56);
+ vgawb_3d(0x3c9, 100);
+ vgawb_3d(0x3c9, 160);
+
+ vgawb_3d(0x3c8, 254);
+ vgawb_3d(0x3c9, 0);
+ vgawb_3d(0x3c9, 0);
+ vgawb_3d(0x3c9, 0);
+
+ /* Disable hardware cursor */
+ vgawb_3d(S3_CRTC_ADR, S3_REG_LOCK2);
+ vgawb_3d(S3_CRTC_DATA, 0xa0);
+ vgawb_3d(S3_CRTC_ADR, S3_HGC_MODE);
+ vgawb_3d(S3_CRTC_DATA, 0x00);
+ vgawb_3d(S3_CRTC_ADR, S3_HWGC_DX);
+ vgawb_3d(S3_CRTC_DATA, 0x00);
+ vgawb_3d(S3_CRTC_ADR, S3_HWGC_DY);
+ vgawb_3d(S3_CRTC_DATA, 0x00);
+
+ return 0; /* TODO: hardware cursor for CV64/3D */
+}
+
+
+/*
+ * This function should fill in the `fix' structure based on the
+ * values in the `par' structure.
+ */
+
+static int Cyber_encode_fix(struct fb_fix_screeninfo *fix,
+ struct virgefb_par *par)
+{
+ int i;
+
+ strcpy(fix->id, virgefb_name);
+ fix->smem_start = (caddr_t)CyberMem;
+ fix->smem_len = CyberSize;
+ fix->mmio_start = (unsigned char *)CyberRegs;
+ fix->mmio_len = 0x10000; /* TODO: verify this for the CV64/3D */
+
+ fix->type = FB_TYPE_PACKED_PIXELS;
+ fix->type_aux = 0;
+ if (par->bpp == 8)
+ fix->visual = FB_VISUAL_PSEUDOCOLOR;
+ else
+ fix->visual = FB_VISUAL_DIRECTCOLOR;
+
+ fix->xpanstep = 0;
+ fix->ypanstep = 0;
+ fix->ywrapstep = 0;
+ fix->line_length = 0;
+
+ for (i = 0; i < arraysize(fix->reserved); i++)
+ fix->reserved[i] = 0;
+
+ return(0);
+}
+
+
+/*
+ * Get the video params out of `var'. If a value doesn't fit, round
+ * it up, if it's too big, return -EINVAL.
+ */
+
+static int Cyber_decode_var(struct fb_var_screeninfo *var,
+ struct virgefb_par *par)
+{
+#if 1
+ par->xres = var->xres;
+ par->yres = var->yres;
+ par->bpp = var->bits_per_pixel;
+#else
+ if (Cyberfb_Cyber8) {
+ par->xres = VIRGE8_WIDTH;
+ par->yres = VIRGE8_HEIGHT;
+ par->bpp = 8;
+ } else {
+ par->xres = VIRGE16_WIDTH;
+ par->yres = VIRGE16_HEIGHT;
+ par->bpp = 16;
+ }
+#endif
+ return(0);
+}
+
+
+/*
+ * Fill the `var' structure based on the values in `par' and maybe
+ * other values read out of the hardware.
+ */
+
+static int Cyber_encode_var(struct fb_var_screeninfo *var,
+ struct virgefb_par *par)
+{
+ int i;
+
+ var->xres = par->xres;
+ var->yres = par->yres;
+ var->xres_virtual = par->xres;
+ var->yres_virtual = par->yres;
+ var->xoffset = 0;
+ var->yoffset = 0;
+
+ var->bits_per_pixel = par->bpp;
+ var->grayscale = 0;
+
+ if (par->bpp == 8) {
+ var->red.offset = 0;
+ var->red.length = 8;
+ var->red.msb_right = 0;
+ var->blue = var->green = var->red;
+ } else {
+ var->red.offset = 11;
+ var->red.length = 5;
+ var->red.msb_right = 0;
+ var->green.offset = 5;
+ var->green.length = 6;
+ var->green.msb_right = 0;
+ var->blue.offset = 0;
+ var->blue.length = 5;
+ var->blue.msb_right = 0;
+ }
+ var->transp.offset = 0;
+ var->transp.length = 0;
+ var->transp.msb_right = 0;
+
+ var->nonstd = 0;
+ var->activate = 0;
+
+ var->height = -1;
+ var->width = -1;
+
+ var->accel = FB_ACCEL_S3VIRGE;
+ DPRINTK("accel CV64/3D\n");
+
+ var->vmode = FB_VMODE_NONINTERLACED;
+
+ /* Dummy values */
+
+ if (par->bpp == 8)
+ var->pixclock = VIRGE8_PIXCLOCK;
+ else
+ var->pixclock = VIRGE16_PIXCLOCK;
+ var->sync = 0;
+ var->left_margin = 64;
+ var->right_margin = 96;
+ var->upper_margin = 35;
+ var->lower_margin = 12;
+ var->hsync_len = 112;
+ var->vsync_len = 2;
+
+ for (i = 0; i < arraysize(var->reserved); i++)
+ var->reserved[i] = 0;
+
+ return(0);
+}
+
+
+/*
+ * Set a single color register. The values supplied are already
+ * rounded down to the hardware's capabilities (according to the
+ * entries in the var structure). Return != 0 for invalid regno.
+ */
+
+static int Cyber_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
+ u_int transp, struct fb_info *info)
+{
+ if (regno > 255)
+ {
+ return (1);
+ }
+
+ /*
+ * No colors on the CV3D yet.
+ */
+
+ vgawb_3d(0x3c8, (unsigned char) regno);
+ Cyber_colour_table [regno][0] = red & 0xff;
+ Cyber_colour_table [regno][1] = green & 0xff;
+ Cyber_colour_table [regno][2] = blue & 0xff;
+ Cyber_colour_table [regno][3] = transp;
+
+ vgawb_3d(0x3c9, ((red & 0xff) >> 2));
+ vgawb_3d(0x3c9, ((green & 0xff) >> 2));
+ vgawb_3d(0x3c9, ((blue & 0xff) >> 2));
+
+ return (0);
+}
+
+
+/*
+ * Read a single color register and split it into
+ * colors/transparent. Return != 0 for invalid regno.
+ */
+
+static int Cyber_getcolreg(u_int regno, u_int *red, u_int *green, u_int *blue,
+ u_int *transp, struct fb_info *info)
+{
+ if (regno >= 256)
+ return (1);
+ *red = Cyber_colour_table [regno][0];
+ *green = Cyber_colour_table [regno][1];
+ *blue = Cyber_colour_table [regno][2];
+ *transp = Cyber_colour_table [regno][3];
+ return (0);
+}
+
+
+/*
+ * (Un)Blank the screen
+ */
+
+void Cyber_blank(int blank)
+{
+ int i;
+
+ if (blank)
+ {
+ for (i = 0; i < 256; i++)
+ {
+ vgawb_3d(0x3c8, (unsigned char) i);
+ vgawb_3d(0x3c9, 0);
+ vgawb_3d(0x3c9, 0);
+ vgawb_3d(0x3c9, 0);
+ }
+ }
+ else
+ {
+ for (i = 0; i < 256; i++)
+ {
+ vgawb_3d(0x3c8, (unsigned char) i);
+ vgawb_3d(0x3c9, Cyber_colour_table[i][0] >> 2);
+ vgawb_3d(0x3c9, Cyber_colour_table[i][1] >> 2);
+ vgawb_3d(0x3c9, Cyber_colour_table[i][2] >> 2);
+ }
+ }
+}
+
+/*
+ * CV3D low-level support
+ */
+
+#define Cyber3D_WaitQueue(v) { do { while ((rl_3d(0x8504) & 0x1f00) < (((v)+2) << 8)); } while (0); }
+
+static inline void Cyber3D_WaitBusy(void)
+{
+unsigned long status;
+
+ do {
+ status = rl_3d(0x8504);
+ } while (!(status & (1 << 13)));
+}
+
+#define S3V_BITBLT (0x0 << 27)
+#define S3V_RECTFILL (0x2 << 27)
+#define S3V_AUTOEXE 0x01
+#define S3V_HWCLIP 0x02
+#define S3V_DRAW 0x20
+#define S3V_DST_8BPP 0x00
+#define S3V_DST_16BPP 0x04
+#define S3V_DST_24BPP 0x08
+#define S3V_MONO_PAT 0x100
+
+#define S3V_BLT_COPY (0xcc<<17)
+#define S3V_BLT_CLEAR (0x00<<17)
+#define S3V_BLT_SET (0xff<<17)
+
+ /*
+ * BitBLT - Through the Plane
+ */
+
+static void Cyber3D_BitBLT(u_short curx, u_short cury, u_short destx,
+ u_short desty, u_short width, u_short height)
+{
+ unsigned int blitcmd = S3V_BITBLT | S3V_DRAW | S3V_DST_8BPP;
+
+ blitcmd |= S3V_BLT_COPY;
+
+ /* Set drawing direction */
+ /* -Y, X maj, -X (default) */
+ if (curx > destx)
+ {
+ blitcmd |= (1 << 25); /* Drawing direction +X */
+ }
+ else
+ {
+ curx += (width - 1);
+ destx += (width - 1);
+ }
+
+ if (cury > desty)
+ {
+ blitcmd |= (1 << 26); /* Drawing direction +Y */
+ }
+ else
+ {
+ cury += (height - 1);
+ desty += (height - 1);
+ }
+
+ wl_3d(0xa4f4, 1); /* pattern fb color */
+
+ wl_3d(0xa4e8, ~0); /* mono pat 0 */
+ wl_3d(0xa4ec, ~0); /* mono pat 1 */
+
+ wl_3d(0xa504, ((width << 16) | height)); /* rwidth_height */
+ wl_3d(0xa508, ((curx << 16) | cury)); /* rsrc_xy */
+ wl_3d(0xa50c, ((destx << 16) | desty)); /* rdest_xy */
+
+ wl_3d(0xa500, blitcmd); /* GO! */
+
+ Cyber3D_WaitBusy();
+}
+
+/*
+ * Rectangle Fill Solid
+ */
+
+static void Cyber3D_RectFill(u_short x, u_short y, u_short width,
+ u_short height, u_short color)
+{
+ unsigned int tmp;
+ unsigned int blitcmd = S3V_RECTFILL | S3V_DRAW | S3V_DST_8BPP |
+ S3V_BLT_CLEAR | S3V_MONO_PAT | (1 << 26) | (1 << 25);
+
+ tmp = color & 0xff;
+ wl_3d(0xa4f4, tmp);
+
+ wl_3d(0xa504, ((width << 16) | height)); /* rwidth_height */
+ wl_3d(0xa50c, ((x << 16) | y)); /* rdest_xy */
+
+ wl_3d(0xa500, blitcmd); /* GO! */
+ Cyber3D_WaitBusy();
+}
+
+
+/**************************************************************
+ * Move cursor to x, y
+ */
+static void Cyber_MoveCursor (u_short x, u_short y)
+{
+ printk("Yuck .... MoveCursor on a 3D\n");
+ return;
+}
+
+
+/* -------------------- Interfaces to hardware functions -------------------- */
+
+
+static struct fb_hwswitch Cyber_switch = {
+ Cyber_init, Cyber_encode_fix, Cyber_decode_var, Cyber_encode_var,
+ Cyber_getcolreg, Cyber_setcolreg, Cyber_blank
+};
+
+
+/* -------------------- Generic routines ------------------------------------ */
+
+
+/*
+ * Fill the hardware's `par' structure.
+ */
+
+static void virgefb_get_par(struct virgefb_par *par)
+{
+ if (current_par_valid)
+ {
+ *par = current_par;
+ }
+ else
+ {
+ fbhw->decode_var(&virgefb_default, par);
+ }
+}
+
+
+static void virgefb_set_par(struct virgefb_par *par)
+{
+ current_par = *par;
+ current_par_valid = 1;
+}
+
+
+static void virge_set_video(struct fb_var_screeninfo *var)
+{
+ /* Set clipping rectangle to current screen size */
+
+ unsigned int clip;
+
+ clip = ((0 << 16) | (var->xres - 1));
+ wl_3d(0xa4dc, clip);
+ clip = ((0 << 16) | (var->yres - 1));
+ wl_3d(0xa4e0, clip);
+}
+
+
+static int do_fb_set_var(struct fb_var_screeninfo *var, int isactive)
+{
+ int err, activate;
+ struct virgefb_par par;
+
+ if ((err = fbhw->decode_var(var, &par)))
+ return(err);
+ activate = var->activate;
+ if ((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW && isactive)
+ virgefb_set_par(&par);
+ fbhw->encode_var(var, &par);
+ var->activate = activate;
+
+ virge_set_video(var);
+ return 0;
+}
+
+
+static void do_install_cmap(int con, struct fb_info *info)
+{
+ if (con != currcon)
+ return;
+ if (fb_display[con].cmap.len)
+ fb_set_cmap(&fb_display[con].cmap, &fb_display[con].var, 1,
+ fbhw->setcolreg, info);
+ else
+ fb_set_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ &fb_display[con].var, 1, fbhw->setcolreg, info);
+}
+
+
+/*
+ * Open/Release the frame buffer device
+ */
+
+static int virgefb_open(struct fb_info *info)
+{
+ /*
+ * Nothing, only a usage count for the moment
+ */
+
+ MOD_INC_USE_COUNT;
+ return(0);
+}
+
+static int virgefb_release(struct fb_info *info)
+{
+ MOD_DEC_USE_COUNT;
+ return(0);
+}
+
+
+/*
+ * Get the Fixed Part of the Display
+ */
+
+static int virgefb_get_fix(struct fb_fix_screeninfo *fix, int con,
+ struct fb_info *info)
+{
+ struct virgefb_par par;
+ int error = 0;
+
+ if (con == -1)
+ virgefb_get_par(&par);
+ else
+ error = fbhw->decode_var(&fb_display[con].var, &par);
+ return(error ? error : fbhw->encode_fix(fix, &par));
+}
+
+
+/*
+ * Get the User Defined Part of the Display
+ */
+
+static int virgefb_get_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ struct virgefb_par par;
+ int error = 0;
+
+ if (con == -1)
+ {
+ virgefb_get_par(&par);
+ error = fbhw->encode_var(var, &par);
+ disp.var = *var; /* ++Andre: don't know if this is the right place */
+ }
+ else
+ {
+ *var = fb_display[con].var;
+ }
+
+ return(error);
+}
+
+
+static void virgefb_set_disp(int con, struct fb_info *info)
+{
+ struct fb_fix_screeninfo fix;
+ struct display *display;
+
+ if (con >= 0)
+ display = &fb_display[con];
+ else
+ display = &disp; /* used during initialization */
+
+ virgefb_get_fix(&fix, con, info);
+ if (con == -1)
+ con = 0;
+ display->screen_base = (u_char *)fix.smem_start;
+ display->visual = fix.visual;
+ display->type = fix.type;
+ display->type_aux = fix.type_aux;
+ display->ypanstep = fix.ypanstep;
+ display->ywrapstep = fix.ywrapstep;
+ display->can_soft_blank = 1;
+ display->inverse = Cyberfb_inverse;
+ switch (display->var.bits_per_pixel) {
+#ifdef CONFIG_FBCON_CFB8
+ case 8:
+ display->dispsw = &fbcon_virge8;
+ break;
+#endif
+#ifdef CONFIG_FBCON_CFB16
+ case 16:
+ display->dispsw = &fbcon_cfb16;
+ break;
+#endif
+ default:
+ display->dispsw = NULL;
+ break;
+ }
+}
+
+
+/*
+ * Set the User Defined Part of the Display
+ */
+
+static int virgefb_set_var(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ int err, oldxres, oldyres, oldvxres, oldvyres, oldbpp;
+
+ if ((err = do_fb_set_var(var, con == currcon)))
+ return(err);
+ if ((var->activate & FB_ACTIVATE_MASK) == FB_ACTIVATE_NOW) {
+ oldxres = fb_display[con].var.xres;
+ oldyres = fb_display[con].var.yres;
+ oldvxres = fb_display[con].var.xres_virtual;
+ oldvyres = fb_display[con].var.yres_virtual;
+ oldbpp = fb_display[con].var.bits_per_pixel;
+ fb_display[con].var = *var;
+ if (oldxres != var->xres || oldyres != var->yres ||
+ oldvxres != var->xres_virtual ||
+ oldvyres != var->yres_virtual ||
+ oldbpp != var->bits_per_pixel) {
+ virgefb_set_disp(con, info);
+ (*fb_info.changevar)(con);
+ fb_alloc_cmap(&fb_display[con].cmap, 0, 0);
+ do_install_cmap(con, info);
+ }
+ }
+ var->activate = 0;
+ return(0);
+}
+
+
+/*
+ * Get the Colormap
+ */
+
+static int virgefb_get_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ if (con == currcon) /* current console? */
+ return(fb_get_cmap(cmap, &fb_display[con].var,
+ kspc, fbhw->getcolreg, info));
+ else if (fb_display[con].cmap.len) /* non default colormap? */
+ fb_copy_cmap(&fb_display[con].cmap, cmap, kspc ? 0 : 2);
+ else
+ fb_copy_cmap(fb_default_cmap(1<<fb_display[con].var.bits_per_pixel),
+ cmap, kspc ? 0 : 2);
+ return(0);
+}
+
+
+/*
+ * Set the Colormap
+ */
+
+static int virgefb_set_cmap(struct fb_cmap *cmap, int kspc, int con,
+ struct fb_info *info)
+{
+ int err;
+
+ if (!fb_display[con].cmap.len) { /* no colormap allocated? */
+ if ((err = fb_alloc_cmap(&fb_display[con].cmap,
+ 1<<fb_display[con].var.bits_per_pixel, 0)))
+ return(err);
+ }
+ if (con == currcon) /* current console? */
+ return(fb_set_cmap(cmap, &fb_display[con].var,
+ kspc, fbhw->setcolreg, info));
+ else
+ fb_copy_cmap(cmap, &fb_display[con].cmap, kspc ? 0 : 1);
+ return(0);
+}
+
+
+/*
+ * Pan or Wrap the Display
+ *
+ * This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
+ */
+
+static int virgefb_pan_display(struct fb_var_screeninfo *var, int con,
+ struct fb_info *info)
+{
+ return(-EINVAL);
+}
+
+
+/*
+ * Cybervision Frame Buffer Specific ioctls
+ */
+
+static int virgefb_ioctl(struct inode *inode, struct file *file,
+ u_int cmd, u_long arg, int con, struct fb_info *info)
+{
+ return(-EINVAL);
+}
+
+
+static struct fb_ops virgefb_ops = {
+ virgefb_open, virgefb_release, virgefb_get_fix, virgefb_get_var,
+ virgefb_set_var, virgefb_get_cmap, virgefb_set_cmap,
+ virgefb_pan_display, NULL, virgefb_ioctl
+};
+
+
+__initfunc(void virgefb_setup(char *options, int *ints))
+{
+ char *this_opt;
+
+ fb_info.fontname[0] = '\0';
+
+ if (!options || !*options)
+ return;
+
+ for (this_opt = strtok(options, ","); this_opt; this_opt = strtok(NULL, ","))
+ if (!strcmp(this_opt, "inverse")) {
+ Cyberfb_inverse = 1;
+ fb_invert_cmaps();
+ } else if (!strncmp(this_opt, "font:", 5))
+ strcpy(fb_info.fontname, this_opt+5);
+ else if (!strcmp (this_opt, "virge8")){
+ virgefb_default = virgefb_predefined[VIRGE8_DEFMODE].var;
+ }
+ else if (!strcmp (this_opt, "virge16")){
+ virgefb_default = virgefb_predefined[VIRGE16_DEFMODE].var;
+ }
+ else
+ get_video_mode(this_opt);
+
+ DPRINTK("default mode: xres=%d, yres=%d, bpp=%d\n",virgefb_default.xres,
+ virgefb_default.yres,
+ virgefb_default.bits_per_pixel);
+}
+
+
+/*
+ * Initialization
+ */
+
+__initfunc(unsigned long virgefb_init(unsigned long mem_start))
+{
+ int err;
+ struct virgefb_par par;
+ unsigned long board_addr;
+ const struct ConfigDev *cd;
+
+ if (!(CyberKey = zorro_find(ZORRO_PROD_PHASE5_CYBERVISION64_3D, 0, 0)))
+ return mem_start;
+
+ cd = zorro_get_board (CyberKey);
+ zorro_config_board (CyberKey, 0);
+ board_addr = (unsigned long)cd->cd_BoardAddr;
+
+ /* This includes the video memory as well as the S3 register set */
+ if ((unsigned long)cd->cd_BoardAddr < 0x01000000)
+ {
+ /*
+ * Ok we got the board running in Z2 space.
+ */
+
+ CyberMem = ZTWO_VADDR(board_addr);
+ printk("CV3D detected running in Z2 mode ... not yet supported!\n");
+ return -ENODEV;
+ }
+ else
+ {
+ CyberVGARegs = kernel_map(board_addr +0x0c000000,
+ 0x00010000,
+ KERNELMAP_NOCACHE_SER,
+ &mem_start);
+ CyberRegs = (char *)kernel_map(board_addr +0x05000000,
+ 0x00010000,
+ KERNELMAP_NOCACHE_SER,
+ &mem_start);
+ CyberMem = kernel_map(board_addr + 0x04800000,
+ 0x00400000,
+ KERNELMAP_NOCACHE_SER,
+ &mem_start);
+ printk("CV3D detected running in Z3 mode\n");
+ }
+
+ fbhw = &Cyber_switch;
+
+ strcpy(fb_info.modename, virgefb_name);
+ fb_info.changevar = NULL;
+ fb_info.node = -1;
+ fb_info.fbops = &virgefb_ops;
+ fb_info.disp = &disp;
+ fb_info.switch_con = &Cyberfb_switch;
+ fb_info.updatevar = &Cyberfb_updatevar;
+ fb_info.blank = &Cyberfb_blank;
+
+ err = register_framebuffer(&fb_info);
+ if (err < 0)
+ return mem_start;
+
+ fbhw->init();
+ fbhw->decode_var(&virgefb_default, &par);
+ fbhw->encode_var(&virgefb_default, &par);
+
+ do_fb_set_var(&virgefb_default, 1);
+ virgefb_get_var(&fb_display[0].var, -1, &fb_info);
+ virgefb_set_disp(-1, &fb_info);
+ do_install_cmap(0, &fb_info);
+
+ printk("fb%d: %s frame buffer device, using %ldK of video memory\n",
+ GET_FB_IDX(fb_info.node), fb_info.modename, CyberSize>>10);
+
+ /* TODO: This driver cannot be unloaded yet */
+ MOD_INC_USE_COUNT;
+
+ return mem_start;
+}
+
+
+static int Cyberfb_switch(int con, struct fb_info *info)
+{
+ /* Do we have to save the colormap? */
+ if (fb_display[currcon].cmap.len)
+ fb_get_cmap(&fb_display[currcon].cmap, &fb_display[currcon].var, 1,
+ fbhw->getcolreg, info);
+
+ do_fb_set_var(&fb_display[con].var, 1);
+ currcon = con;
+ /* Install new colormap */
+ do_install_cmap(con, info);
+ return(0);
+}
+
+
+/*
+ * Update the `var' structure (called by fbcon.c)
+ *
+ * This call looks only at yoffset and the FB_VMODE_YWRAP flag in `var'.
+ * Since it's called by a kernel driver, no range checking is done.
+ */
+
+static int Cyberfb_updatevar(int con, struct fb_info *info)
+{
+ return(0);
+}
+
+
+/*
+ * Blank the display.
+ */
+
+static void Cyberfb_blank(int blank, struct fb_info *info)
+{
+ fbhw->blank(blank);
+}
+
+
+/*
+ * Get a Video Mode
+ */
+
+__initfunc(static int get_video_mode(const char *name))
+{
+ int i;
+
+ for (i = 0; i < NUM_TOTAL_MODES; i++) {
+ if (!strcmp(name, virgefb_predefined[i].name)) {
+ virgefb_default = virgefb_predefined[i].var;
+ return(i);
+ }
+ }
+ /* ++Andre: set virgefb default mode */
+ virgefb_default = virgefb_predefined[VIRGE8_DEFMODE].var;
+ return(0);
+}
+
+
+/*
+ * Text console acceleration
+ */
+
+#ifdef CONFIG_FBCON_CFB8
+static void fbcon_virge8_bmove(struct display *p, int sy, int sx, int dy,
+ int dx, int height, int width)
+{
+ sx *= 8; dx *= 8; width *= 8;
+ Cyber3D_BitBLT((u_short)sx, (u_short)(sy*p->fontheight), (u_short)dx,
+ (u_short)(dy*p->fontheight), (u_short)width,
+ (u_short)(height*p->fontheight));
+}
+
+static void fbcon_virge8_clear(struct vc_data *conp, struct display *p, int sy,
+ int sx, int height, int width)
+{
+ unsigned char bg;
+
+ sx *= 8; width *= 8;
+ bg = attr_bgcol_ec(p,conp);
+ Cyber3D_RectFill((u_short)sx, (u_short)(sy*p->fontheight),
+ (u_short)width, (u_short)(height*p->fontheight),
+ (u_short)bg);
+}
+
+static struct display_switch fbcon_virge8 = {
+ fbcon_cfb8_setup, fbcon_virge8_bmove, fbcon_virge8_clear, fbcon_cfb8_putc,
+ fbcon_cfb8_putcs, fbcon_cfb8_revc
+};
+#endif
+
+
+#ifdef MODULE
+int init_module(void)
+{
+ return(virgefb_init(NULL));
+}
+
+void cleanup_module(void)
+{
+ /* Not reached because the usecount will never be
+ decremented to zero */
+ unregister_framebuffer(&fb_info);
+ /* TODO: clean up ... */
+}
+#endif /* MODULE */