⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 fbdev.c

📁 linux-2.4.29操作系统的源码
💻 C
📖 第 1 页 / 共 4 页
字号:
/* * linux/drivers/video/riva/fbdev.c * * nVidia RIVA 128/TNT/TNT2/GeForce2/3 fb driver * * Maintained by Ani Joshi <ajoshi@kernel.crashing.org> * * Copyright 1999-2000 Jeff Garzik * Copyright 2000-2003 Ani Joshi * * Contributors: * *	Ani Joshi:  Lots of debugging and cleanup work, really helped *	get the driver going * *	Ferenc Bakonyi:  Bug fixes, cleanup, modularization * *	Jindrich Makovicka:  Accel code help, hw cursor, mtrr * * Initial template from skeletonfb.c, created 28 Dec 1997 by Geert Uytterhoeven * Includes riva_hw.c from nVidia, see copyright below. * KGI code provided the basis for state storage, init, and mode switching. * * 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. * * Known bugs and issues: *	restoring text mode fails *	doublescan modes are broken *	option 'noaccel' has no effect */#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/selection.h>#include <linux/tty.h>#include <linux/slab.h>#include <linux/delay.h>#include <linux/fb.h>#include <linux/init.h>#include <linux/pci.h>#include <linux/console.h>#ifdef CONFIG_MTRR#include <asm/mtrr.h>#endif#include "rivafb.h"#include "nvreg.h"#ifndef CONFIG_PCI		/* sanity check */#error This driver requires PCI support.#endif/* version number of this driver */#define RIVAFB_VERSION "0.9.4"/* ------------------------------------------------------------------------- * * * various helpful macros and constants * * ------------------------------------------------------------------------- */#undef RIVAFBDEBUG#ifdef RIVAFBDEBUG#define DPRINTK(fmt, args...) printk(KERN_DEBUG "%s: " fmt, __FUNCTION__ , ## args)#else#define DPRINTK(fmt, args...)#endif#ifndef RIVA_NDEBUG#define assert(expr) \	if(!(expr)) { \	printk( "Assertion failed! %s,%s,%s,line=%d\n",\	#expr,__FILE__,__FUNCTION__,__LINE__); \	BUG(); \	}#else#define assert(expr)#endif#define PFX "rivafb: "/* macro that allows you to set overflow bits */#define SetBitField(value,from,to) SetBF(to,GetBF(value,from))#define SetBit(n)		(1<<(n))#define Set8Bits(value)		((value)&0xff)/* HW cursor parameters */#define DEFAULT_CURSOR_BLINK_RATE	(40)#define CURSOR_HIDE_DELAY		(20)#define CURSOR_SHOW_DELAY		(3)#ifdef __BIG_ENDIAN#define CURSOR_COLOR		0xff7f#else#define CURSOR_COLOR		0x7fff#endif#define TRANSPARENT_COLOR	0x0000#define MAX_CURS		32/* ------------------------------------------------------------------------- * * * prototypes * * ------------------------------------------------------------------------- */static void rivafb_blank(int blank, struct fb_info *info);extern void riva_setup_accel(struct rivafb_info *rinfo);extern void wait_for_idle(struct rivafb_info *rinfo);/* ------------------------------------------------------------------------- * * * card identification * * ------------------------------------------------------------------------- */enum riva_chips {	CH_RIVA_128 = 0,	CH_RIVA_TNT,	CH_RIVA_TNT2,	CH_RIVA_UTNT2,	/* UTNT2 */	CH_RIVA_VTNT2,	/* VTNT2 */	CH_RIVA_UVTNT2,	/* VTNT2 */	CH_RIVA_ITNT2,	/* ITNT2 */	CH_GEFORCE_SDR,	CH_GEFORCE_DDR,	CH_QUADRO,	CH_GEFORCE2_MX,	CH_QUADRO2_MXR,	CH_GEFORCE2_GTS,	CH_GEFORCE2_ULTRA,	CH_QUADRO2_PRO,	CH_GEFORCE2_GO,        CH_GEFORCE3,        CH_GEFORCE3_1,        CH_GEFORCE3_2,        CH_QUADRO_DDC};/* directly indexed by riva_chips enum, above */static struct riva_chip_info {	const char *name;	unsigned arch_rev;} riva_chip_info[] __devinitdata = {	{ "RIVA-128", NV_ARCH_03 },	{ "RIVA-TNT", NV_ARCH_04 },	{ "RIVA-TNT2", NV_ARCH_04 },	{ "RIVA-UTNT2", NV_ARCH_04 },	{ "RIVA-VTNT2", NV_ARCH_04 },	{ "RIVA-UVTNT2", NV_ARCH_04 },	{ "RIVA-ITNT2", NV_ARCH_04 },	{ "GeForce-SDR", NV_ARCH_10},	{ "GeForce-DDR", NV_ARCH_10},	{ "Quadro", NV_ARCH_10},	{ "GeForce2-MX", NV_ARCH_10},	{ "Quadro2-MXR", NV_ARCH_10},	{ "GeForce2-GTS", NV_ARCH_10},	{ "GeForce2-ULTRA", NV_ARCH_10},	{ "Quadro2-PRO", NV_ARCH_10},        { "GeForce2-Go", NV_ARCH_10},        { "GeForce3", NV_ARCH_20},         { "GeForce3 Ti 200", NV_ARCH_20},        { "GeForce3 Ti 500", NV_ARCH_20},        { "Quadro DDC", NV_ARCH_20}};static struct pci_device_id rivafb_pci_tbl[] __devinitdata = {	{ PCI_VENDOR_ID_NVIDIA_SGS, PCI_DEVICE_ID_NVIDIA_SGS_RIVA128,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_128 },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_TNT,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_TNT },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_TNT2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_TNT2 },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_UTNT2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_UTNT2 },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_VTNT2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_VTNT2 },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_UVTNT2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_VTNT2 },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_ITNT2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_RIVA_ITNT2 },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE_SDR,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE_SDR },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE_DDR,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE_DDR },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_QUADRO },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_MX,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE2_MX },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_MX2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE2_MX },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO2_MXR,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_QUADRO2_MXR },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_GTS,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE2_GTS },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_GTS2,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE2_GTS },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_ULTRA,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE2_ULTRA },	{ PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO2_PRO,	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_QUADRO2_PRO },        { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_GO,          PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE2_GO },        { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE3,          PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE3 },        { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE3_1,          PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE3_1 },        { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE3_2,          PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_GEFORCE3_2 },        { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO_DDC,          PCI_ANY_ID, PCI_ANY_ID, 0, 0, CH_QUADRO_DDC },	{ 0, } /* terminate list */};MODULE_DEVICE_TABLE(pci, rivafb_pci_tbl);/* ------------------------------------------------------------------------- * * * framebuffer related structures * * ------------------------------------------------------------------------- */#ifdef FBCON_HAS_CFB8extern struct display_switch fbcon_riva8;#endif#ifdef FBCON_HAS_CFB16extern struct display_switch fbcon_riva16;#endif#ifdef FBCON_HAS_CFB32extern struct display_switch fbcon_riva32;#endif#if 0/* describes the state of a Riva board */struct rivafb_par {	struct riva_regs state;	/* state of hw board */	__u32 visual;		/* FB_VISUAL_xxx */	unsigned depth;		/* bpp of current mode */};#endifstruct riva_cursor {	int enable;	int on;	int vbl_cnt;	int last_move_delay;	int blink_rate;	struct {		u16 x, y;	} pos, size;	unsigned short image[MAX_CURS*MAX_CURS];	struct timer_list *timer;};/* ------------------------------------------------------------------------- * * * global variables * * ------------------------------------------------------------------------- */struct rivafb_info *riva_boards = NULL;/* command line data, set in rivafb_setup() */static char fontname[40] __initdata = { 0 };static char noaccel __initdata = 0;static char nomove = 0;static char nohwcursor __initdata = 0;static char noblink = 0;#ifdef CONFIG_MTRRstatic char nomtrr __initdata = 0;#endif#ifndef MODULEstatic char *mode_option __initdata = NULL;#elsestatic char *font = NULL;#endifstatic struct fb_var_screeninfo rivafb_default_var = {	xres:		640,	yres:		480,	xres_virtual:	640,	yres_virtual:	480,	xoffset:	0,	yoffset:	0,	bits_per_pixel:	8,	grayscale:	0,	red:		{0, 6, 0},	green:		{0, 6, 0},	blue:		{0, 6, 0},	transp:		{0, 0, 0},	nonstd:		0,	activate:	0,	height:		-1,	width:		-1,	accel_flags:	0,	pixclock:	39721,	left_margin:	40,	right_margin:	24,	upper_margin:	32,	lower_margin:	11,	hsync_len:	96,	vsync_len:	2,	sync:		0,	vmode:		FB_VMODE_NONINTERLACED};/* from GGI */static const struct riva_regs reg_template = {	{0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,	/* ATTR */	 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,	 0x41, 0x01, 0x0F, 0x00, 0x00},	{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,	/* CRT  */	 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00,	 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE3,	/* 0x10 */	 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,	 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,	/* 0x20 */	 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,	 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,	/* 0x30 */	 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,	 0x00,							/* 0x40 */	 },	{0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x05, 0x0F,	/* GRA  */	 0xFF},	{0x03, 0x01, 0x0F, 0x00, 0x0E},				/* SEQ  */	0xEB							/* MISC */};/* ------------------------------------------------------------------------- * * * MMIO access macros * * ------------------------------------------------------------------------- */static inline void CRTCout(struct rivafb_info *rinfo, unsigned char index,			   unsigned char val){	VGA_WR08(rinfo->riva.PCIO, 0x3d4, index);	VGA_WR08(rinfo->riva.PCIO, 0x3d5, val);}static inline unsigned char CRTCin(struct rivafb_info *rinfo,				   unsigned char index){	VGA_WR08(rinfo->riva.PCIO, 0x3d4, index);	return (VGA_RD08(rinfo->riva.PCIO, 0x3d5));}static inline void GRAout(struct rivafb_info *rinfo, unsigned char index,			  unsigned char val){	VGA_WR08(rinfo->riva.PVIO, 0x3ce, index);	VGA_WR08(rinfo->riva.PVIO, 0x3cf, val);}static inline unsigned char GRAin(struct rivafb_info *rinfo,				  unsigned char index){	VGA_WR08(rinfo->riva.PVIO, 0x3ce, index);	return (VGA_RD08(rinfo->riva.PVIO, 0x3cf));}static inline void SEQout(struct rivafb_info *rinfo, unsigned char index,			  unsigned char val){	VGA_WR08(rinfo->riva.PVIO, 0x3c4, index);	VGA_WR08(rinfo->riva.PVIO, 0x3c5, val);}static inline unsigned char SEQin(struct rivafb_info *rinfo,				  unsigned char index){	VGA_WR08(rinfo->riva.PVIO, 0x3c4, index);	return (VGA_RD08(rinfo->riva.PVIO, 0x3c5));}static inline void ATTRout(struct rivafb_info *rinfo, unsigned char index,			   unsigned char val){	VGA_WR08(rinfo->riva.PCIO, 0x3c0, index);	VGA_WR08(rinfo->riva.PCIO, 0x3c0, val);}static inline unsigned char ATTRin(struct rivafb_info *rinfo,				   unsigned char index){	VGA_WR08(rinfo->riva.PCIO, 0x3c0, index);	return (VGA_RD08(rinfo->riva.PCIO, 0x3c1));}static inline void MISCout(struct rivafb_info *rinfo, unsigned char val){	VGA_WR08(rinfo->riva.PVIO, 0x3c2, val);}static inline unsigned char MISCin(struct rivafb_info *rinfo){	return (VGA_RD08(rinfo->riva.PVIO, 0x3cc));}/* ------------------------------------------------------------------------- * * * cursor stuff * * ------------------------------------------------------------------------- *//** * riva_cursor_timer_handler - blink timer * @dev_addr: pointer to rivafb_info object containing info for current riva board * * DESCRIPTION: * Cursor blink timer. */static void riva_cursor_timer_handler(unsigned long dev_addr){	struct rivafb_info *rinfo = (struct rivafb_info *)dev_addr;	if (!rinfo->cursor) return;	if (!rinfo->cursor->enable) goto out;	if (rinfo->cursor->last_move_delay < 1000)		rinfo->cursor->last_move_delay++;	if (rinfo->cursor->vbl_cnt && --rinfo->cursor->vbl_cnt == 0) {		rinfo->cursor->on ^= 1;		if (rinfo->cursor->on)			*(rinfo->riva.CURSORPOS) = (rinfo->cursor->pos.x & 0xFFFF)						   | (rinfo->cursor->pos.y << 16);		rinfo->riva.ShowHideCursor(&rinfo->riva, rinfo->cursor->on);		if (!noblink)			rinfo->cursor->vbl_cnt = rinfo->cursor->blink_rate;	}out:	rinfo->cursor->timer->expires = jiffies + (HZ / 100);	add_timer(rinfo->cursor->timer);}/** * rivafb_init_cursor - allocates cursor structure and starts blink timer * @rinfo: pointer to rivafb_info object containing info for current riva board * * DESCRIPTION: * Allocates cursor structure and starts blink timer. * * RETURNS: * Pointer to allocated cursor structure. * * CALLED FROM: * rivafb_init_one() */static struct riva_cursor * __init rivafb_init_cursor(struct rivafb_info *rinfo){	struct riva_cursor *cursor;	cursor = kmalloc(sizeof(struct riva_cursor), GFP_KERNEL);	if (!cursor) return 0;	memset(cursor, 0, sizeof(*cursor));	cursor->timer = kmalloc(sizeof(*cursor->timer), GFP_KERNEL);	if (!cursor->timer) {		kfree(cursor);		return 0;	}	memset(cursor->timer, 0, sizeof(*cursor->timer));	cursor->blink_rate = DEFAULT_CURSOR_BLINK_RATE;	init_timer(cursor->timer);	cursor->timer->expires = jiffies + (HZ / 100);	cursor->timer->data = (unsigned long)rinfo;	cursor->timer->function = riva_cursor_timer_handler;	add_timer(cursor->timer);	return cursor;}/** * rivafb_exit_cursor - stops blink timer and releases cursor structure * @rinfo: pointer to rivafb_info object containing info for current riva board * * DESCRIPTION: * Stops blink timer and releases cursor structure. * * CALLED FROM: * rivafb_init_one() * rivafb_remove_one() */static void rivafb_exit_cursor(struct rivafb_info *rinfo){	struct riva_cursor *cursor = rinfo->cursor;	if (cursor) {		if (cursor->timer) {			del_timer_sync(cursor->timer);			kfree(cursor->timer);		}		kfree(cursor);		rinfo->cursor = 0;	}}/** * rivafb_download_cursor - writes cursor shape into card registers * @rinfo: pointer to rivafb_info object containing info for current riva board * * DESCRIPTION: * Writes cursor shape into card registers. * * CALLED FROM: * riva_load_video_mode() */static void rivafb_download_cursor(struct rivafb_info *rinfo){	int i, save;	int *image;		if (!rinfo->cursor) return;	image = (int *)rinfo->cursor->image;	save = rinfo->riva.ShowHideCursor(&rinfo->riva, 0);	for (i = 0; i < (MAX_CURS*MAX_CURS*2)/sizeof(int); i++)		writel(image[i], rinfo->riva.CURSOR + i);	rinfo->riva.ShowHideCursor(&rinfo->riva, save);}/** * rivafb_create_cursor - sets rectangular cursor * @rinfo: pointer to rivafb_info object containing info for current riva board * @width: cursor width in pixels * @height: cursor height in pixels * * DESCRIPTION: * Sets rectangular cursor. * * CALLED FROM: * rivafb_set_font() * rivafb_set_var() */static void rivafb_create_cursor(struct rivafb_info *rinfo, int width, int height){	struct riva_cursor *c = rinfo->cursor;	int i, j, idx;	if (c) {		if (width <= 0 || height <= 0) {			width = 8;			height = 16;		}		if (width > MAX_CURS) width = MAX_CURS;		if (height > MAX_CURS) height = MAX_CURS;		c->size.x = width;		c->size.y = height;				idx = 0;		for (i = 0; i < height; i++) {			for (j = 0; j < width; j++,idx++)				c->image[idx] = CURSOR_COLOR;			for (j = width; j < MAX_CURS; j++,idx++)				c->image[idx] = TRANSPARENT_COLOR;		}		for (i = height; i < MAX_CURS; i++)			for (j = 0; j < MAX_CURS; j++,idx++)				c->image[idx] = TRANSPARENT_COLOR;	}}/** * rivafb_set_font - change font size

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -