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

📄 stifb.c

📁 Linux Kernel 2.6.9 for OMAP1710
💻 C
📖 第 1 页 / 共 3 页
字号:
static voidelkSetupPlanes(struct stifb_info *fb){	SETUP_RAMDAC(fb);	SETUP_FB(fb);}static void ngleSetupAttrPlanes(struct stifb_info *fb, int BufferNumber){	SETUP_ATTR_ACCESS(fb, BufferNumber);	SET_ATTR_SIZE(fb, fb->info.var.xres, fb->info.var.yres);	FINISH_ATTR_ACCESS(fb);	SETUP_FB(fb);}static voidrattlerSetupPlanes(struct stifb_info *fb){	CRX24_SETUP_RAMDAC(fb);    	/* replacement for: SETUP_FB(fb, CRX24_OVERLAY_PLANES); */	WRITE_WORD(0x83000300, fb, REG_14);	SETUP_HW(fb);	WRITE_BYTE(1, fb, REG_16b1);	fb_memset(fb->info.fix.smem_start, 0xff,		fb->info.var.yres*fb->info.fix.line_length);    	CRX24_SET_OVLY_MASK(fb);	SETUP_FB(fb);}#define HYPER_CMAP_TYPE				0#define NGLE_CMAP_INDEXED0_TYPE			0#define NGLE_CMAP_OVERLAY_TYPE			3/* typedef of LUT (Colormap) BLT Control Register */typedef union	/* Note assumption that fields are packed left-to-right */{	u32 all;	struct	{		unsigned enable              :  1;		unsigned waitBlank           :  1;		unsigned reserved1           :  4;		unsigned lutOffset           : 10;   /* Within destination LUT */		unsigned lutType             :  2;   /* Cursor, image, overlay */		unsigned reserved2           :  4;		unsigned length              : 10;	} fields;} NgleLutBltCtl;#if 0static NgleLutBltCtlsetNgleLutBltCtl(struct stifb_info *fb, int offsetWithinLut, int length){	NgleLutBltCtl lutBltCtl;	/* set enable, zero reserved fields */	lutBltCtl.all           = 0x80000000;	lutBltCtl.fields.length = length;	switch (fb->id) 	{	case S9000_ID_A1439A:		/* CRX24 */		if (fb->var.bits_per_pixel == 8) {			lutBltCtl.fields.lutType = NGLE_CMAP_OVERLAY_TYPE;			lutBltCtl.fields.lutOffset = 0;		} else {			lutBltCtl.fields.lutType = NGLE_CMAP_INDEXED0_TYPE;			lutBltCtl.fields.lutOffset = 0 * 256;		}		break;			case S9000_ID_ARTIST:		lutBltCtl.fields.lutType = NGLE_CMAP_INDEXED0_TYPE;		lutBltCtl.fields.lutOffset = 0 * 256;		break;			default:		lutBltCtl.fields.lutType = NGLE_CMAP_INDEXED0_TYPE;		lutBltCtl.fields.lutOffset = 0;		break;	}	/* Offset points to start of LUT.  Adjust for within LUT */	lutBltCtl.fields.lutOffset += offsetWithinLut;	return lutBltCtl;}#endifstatic NgleLutBltCtlsetHyperLutBltCtl(struct stifb_info *fb, int offsetWithinLut, int length) {	NgleLutBltCtl lutBltCtl;	/* set enable, zero reserved fields */	lutBltCtl.all = 0x80000000;	lutBltCtl.fields.length = length;	lutBltCtl.fields.lutType = HYPER_CMAP_TYPE;	/* Expect lutIndex to be 0 or 1 for image cmaps, 2 or 3 for overlay cmaps */	if (fb->info.var.bits_per_pixel == 8)		lutBltCtl.fields.lutOffset = 2 * 256;	else		lutBltCtl.fields.lutOffset = 0 * 256;	/* Offset points to start of LUT.  Adjust for within LUT */	lutBltCtl.fields.lutOffset += offsetWithinLut;	return lutBltCtl;}static void hyperUndoITE(struct stifb_info *fb){	int nFreeFifoSlots = 0;	u32 fbAddr;	NGLE_LOCK(fb);	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 1);	WRITE_WORD(0xffffffff, fb, REG_32);	/* Write overlay transparency mask so only entry 255 is transparent */	/* Hardware setup for full-depth write to "magic" location */	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 7);	NGLE_QUICK_SET_DST_BM_ACCESS(fb, 		BA(IndexedDcd, Otc04, Ots08, AddrLong,		BAJustPoint(0), BINovly, BAIndexBase(0)));	NGLE_QUICK_SET_IMAGE_BITMAP_OP(fb,		IBOvals(RopSrc, MaskAddrOffset(0),		BitmapExtent08, StaticReg(0),		DataDynamic, MaskOtc, BGx(0), FGx(0)));	/* Now prepare to write to the "magic" location */	fbAddr = NGLE_LONG_FB_ADDRESS(0, 1532, 0);	NGLE_BINC_SET_DSTADDR(fb, fbAddr);	NGLE_REALLY_SET_IMAGE_PLANEMASK(fb, 0xffffff);	NGLE_BINC_SET_DSTMASK(fb, 0xffffffff);	/* Finally, write a zero to clear the mask */	NGLE_BINC_WRITE32(fb, 0);	NGLE_UNLOCK(fb);}static void ngleDepth8_ClearImagePlanes(struct stifb_info *fb){	/* FIXME! */}static void ngleDepth24_ClearImagePlanes(struct stifb_info *fb){	/* FIXME! */}static voidngleResetAttrPlanes(struct stifb_info *fb, unsigned int ctlPlaneReg){	int nFreeFifoSlots = 0;	u32 packed_dst;	u32 packed_len;	NGLE_LOCK(fb);	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 4);	NGLE_QUICK_SET_DST_BM_ACCESS(fb, 				     BA(IndexedDcd, Otc32, OtsIndirect,					AddrLong, BAJustPoint(0),					BINattr, BAIndexBase(0)));	NGLE_QUICK_SET_CTL_PLN_REG(fb, ctlPlaneReg);	NGLE_SET_TRANSFERDATA(fb, 0xffffffff);	NGLE_QUICK_SET_IMAGE_BITMAP_OP(fb,				       IBOvals(RopSrc, MaskAddrOffset(0),					       BitmapExtent08, StaticReg(1),					       DataDynamic, MaskOtc,					       BGx(0), FGx(0)));	packed_dst = 0;	packed_len = (fb->info.var.xres << 16) | fb->info.var.yres;	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 2);	NGLE_SET_DSTXY(fb, packed_dst);	SET_LENXY_START_RECFILL(fb, packed_len);	/*	 * In order to work around an ELK hardware problem (Buffy doesn't	 * always flush it's buffers when writing to the attribute	 * planes), at least 4 pixels must be written to the attribute	 * planes starting at (X == 1280) and (Y != to the last Y written	 * by BIF):	 */	if (fb->id == S9000_ID_A1659A) {   /* ELK_DEVICE_ID */		/* It's safe to use scanline zero: */		packed_dst = (1280 << 16);		GET_FIFO_SLOTS(fb, nFreeFifoSlots, 2);		NGLE_SET_DSTXY(fb, packed_dst);		packed_len = (4 << 16) | 1;		SET_LENXY_START_RECFILL(fb, packed_len);	}   /* ELK Hardware Kludge */	/**** Finally, set the Control Plane Register back to zero: ****/	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 1);	NGLE_QUICK_SET_CTL_PLN_REG(fb, 0);		NGLE_UNLOCK(fb);}    static voidngleClearOverlayPlanes(struct stifb_info *fb, int mask, int data){	int nFreeFifoSlots = 0;	u32 packed_dst;	u32 packed_len;    	NGLE_LOCK(fb);	/* Hardware setup */	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 8);	NGLE_QUICK_SET_DST_BM_ACCESS(fb, 				     BA(IndexedDcd, Otc04, Ots08, AddrLong,					BAJustPoint(0), BINovly, BAIndexBase(0)));        NGLE_SET_TRANSFERDATA(fb, 0xffffffff);  /* Write foreground color */        NGLE_REALLY_SET_IMAGE_FG_COLOR(fb, data);        NGLE_REALLY_SET_IMAGE_PLANEMASK(fb, mask);            packed_dst = 0;        packed_len = (fb->info.var.xres << 16) | fb->info.var.yres;        NGLE_SET_DSTXY(fb, packed_dst);            /* Write zeroes to overlay planes */		       	NGLE_QUICK_SET_IMAGE_BITMAP_OP(fb,				       IBOvals(RopSrc, MaskAddrOffset(0),					       BitmapExtent08, StaticReg(0),					       DataDynamic, MaskOtc, BGx(0), FGx(0)));		               SET_LENXY_START_RECFILL(fb, packed_len);	NGLE_UNLOCK(fb);}static void hyperResetPlanes(struct stifb_info *fb, int enable){	unsigned int controlPlaneReg;	NGLE_LOCK(fb);	if (IS_24_DEVICE(fb))		if (fb->info.var.bits_per_pixel == 32)			controlPlaneReg = 0x04000F00;		else			controlPlaneReg = 0x00000F00;   /* 0x00000800 should be enought, but lets clear all 4 bits */	else		controlPlaneReg = 0x00000F00; /* 0x00000100 should be enought, but lets clear all 4 bits */	switch (enable) {	case ENABLE:		/* clear screen */		if (IS_24_DEVICE(fb))			ngleDepth24_ClearImagePlanes(fb);		else			ngleDepth8_ClearImagePlanes(fb);		/* Paint attribute planes for default case.		 * On Hyperdrive, this means all windows using overlay cmap 0. */		ngleResetAttrPlanes(fb, controlPlaneReg);		/* clear overlay planes */	        ngleClearOverlayPlanes(fb, 0xff, 255);		/**************************************************		 ** Also need to counteract ITE settings 		 **************************************************/		hyperUndoITE(fb);		break;	case DISABLE:		/* clear screen */		if (IS_24_DEVICE(fb))			ngleDepth24_ClearImagePlanes(fb);		else			ngleDepth8_ClearImagePlanes(fb);		ngleResetAttrPlanes(fb, controlPlaneReg);		ngleClearOverlayPlanes(fb, 0xff, 0);		break;	case -1:	/* RESET */		hyperUndoITE(fb);		ngleResetAttrPlanes(fb, controlPlaneReg);		break;    	}		NGLE_UNLOCK(fb);}/* Return pointer to in-memory structure holding ELK device-dependent ROM values. */static void ngleGetDeviceRomData(struct stifb_info *fb){#if 0XXX: FIXME: !!!	int	*pBytePerLongDevDepData;/* data byte == LSB */	int 	*pRomTable;	NgleDevRomData	*pPackedDevRomData;	int	sizePackedDevRomData = sizeof(*pPackedDevRomData);	char	*pCard8;	int	i;	char	*mapOrigin = NULL;    	int romTableIdx;	pPackedDevRomData = fb->ngle_rom;	SETUP_HW(fb);	if (fb->id == S9000_ID_ARTIST) {		pPackedDevRomData->cursor_pipeline_delay = 4;		pPackedDevRomData->video_interleaves     = 4;	} else {		/* Get pointer to unpacked byte/long data in ROM */		pBytePerLongDevDepData = fb->sti->regions[NGLEDEVDEPROM_CRT_REGION];		/* Tomcat supports several resolutions: 1280x1024, 1024x768, 640x480 */		if (fb->id == S9000_ID_TOMCAT)	{	    /*  jump to the correct ROM table  */	    GET_ROMTABLE_INDEX(romTableIdx);	    while  (romTableIdx > 0)	    {		pCard8 = (Card8 *) pPackedDevRomData;		pRomTable = pBytePerLongDevDepData;		/* Pack every fourth byte from ROM into structure */		for (i = 0; i < sizePackedDevRomData; i++)		{		    *pCard8++ = (Card8) (*pRomTable++);		}		pBytePerLongDevDepData = (Card32 *)			((Card8 *) pBytePerLongDevDepData +			       pPackedDevRomData->sizeof_ngle_data);		romTableIdx--;	    }	}	pCard8 = (Card8 *) pPackedDevRomData;	/* Pack every fourth byte from ROM into structure */	for (i = 0; i < sizePackedDevRomData; i++)	{	    *pCard8++ = (Card8) (*pBytePerLongDevDepData++);	}    }    SETUP_FB(fb);#endif}#define HYPERBOWL_MODE_FOR_8_OVER_88_LUT0_NO_TRANSPARENCIES	4#define HYPERBOWL_MODE01_8_24_LUT0_TRANSPARENT_LUT1_OPAQUE	8#define HYPERBOWL_MODE01_8_24_LUT0_OPAQUE_LUT1_OPAQUE		10#define HYPERBOWL_MODE2_8_24					15/* HCRX specific boot-time initialization */static void __initSETUP_HCRX(struct stifb_info *fb){	int	hyperbowl;        int	nFreeFifoSlots = 0;	if (fb->id != S9000_ID_HCRX)		return;	/* Initialize Hyperbowl registers */	GET_FIFO_SLOTS(fb, nFreeFifoSlots, 7);		if (IS_24_DEVICE(fb)) {		hyperbowl = (fb->info.var.bits_per_pixel == 32) ?			HYPERBOWL_MODE01_8_24_LUT0_TRANSPARENT_LUT1_OPAQUE :			HYPERBOWL_MODE01_8_24_LUT0_OPAQUE_LUT1_OPAQUE;		/* First write to Hyperbowl must happen twice (bug) */		WRITE_WORD(hyperbowl, fb, REG_40);		WRITE_WORD(hyperbowl, fb, REG_40);				WRITE_WORD(HYPERBOWL_MODE2_8_24, fb, REG_39);				WRITE_WORD(0x014c0148, fb, REG_42); /* Set lut 0 to be the direct color */		WRITE_WORD(0x404c4048, fb, REG_43);		WRITE_WORD(0x034c0348, fb, REG_44);		WRITE_WORD(0x444c4448, fb, REG_45);	} else {		hyperbowl = HYPERBOWL_MODE_FOR_8_OVER_88_LUT0_NO_TRANSPARENCIES;		/* First write to Hyperbowl must happen twice (bug) */		WRITE_WORD(hyperbowl, fb, REG_40);		WRITE_WORD(hyperbowl, fb, REG_40);		WRITE_WORD(0x00000000, fb, REG_42);		WRITE_WORD(0x00000000, fb, REG_43);		WRITE_WORD(0x00000000, fb, REG_44);		WRITE_WORD(0x444c4048, fb, REG_45);	}}/* ------------------- driver specific functions --------------------------- */#define TMPBUFLEN 2048static ssize_tstifb_read(struct file *file, char *buf, size_t count, loff_t *ppos){	unsigned long p = *ppos;	struct inode *inode = file->f_dentry->d_inode;	int fbidx = iminor(inode);	struct fb_info *info = registered_fb[fbidx];	char tmpbuf[TMPBUFLEN];	if (!info || ! info->screen_base)		return -ENODEV;	if (p >= info->fix.smem_len)	    return 0;	if (count >= info->fix.smem_len)	    count = info->fix.smem_len;	if (count + p > info->fix.smem_len)		count = info->fix.smem_len - p;	if (count > sizeof(tmpbuf))		count = sizeof(tmpbuf);	if (count) {	    char *base_addr;	    base_addr = info->screen_base;	    memcpy_fromio(&tmpbuf, base_addr+p, count);	    count -= copy_to_user(buf, &tmpbuf, count);	    if (!count)		return -EFAULT;	    *ppos += count;	}	return count;}static ssize_tstifb_write(struct file *file, const char *buf, size_t count, loff_t *ppos){	struct inode *inode = file->f_dentry->d_inode;	int fbidx = iminor(inode);	struct fb_info *info = registered_fb[fbidx];	unsigned long p = *ppos;	size_t c;	int err;	char tmpbuf[TMPBUFLEN];	if (!info || !info->screen_base)		return -ENODEV;	if (p > info->fix.smem_len)	    return -ENOSPC;	if (count >= info->fix.smem_len)	    count = info->fix.smem_len;	err = 0;	if (count + p > info->fix.smem_len) {	    count = info->fix.smem_len - p;	    err = -ENOSPC;	}	p += (unsigned long)info->screen_base;	c = count;	while (c) {	    int len = c > sizeof(tmpbuf) ? sizeof(tmpbuf) : c;	    err = -EFAULT;	    if (copy_from_user(&tmpbuf, buf, len))		    break;	    memcpy_toio(p, &tmpbuf, len);	    c -= len;	    p += len;	    buf += len;	    *ppos += len;

⌨️ 快捷键说明

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