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

📄 cyberfb.c

📁 S3C44B0X下的LCD (framebuffer)驱动资料与相关代码
💻 C
📖 第 1 页 / 共 5 页
字号:
	volatile unsigned char *addr;	static unsigned char cvportbits = 0; /* Mirror port bits here */	DPRINTK("ENTER\n");	addr = base + 0x40001;	if (bits & 0x8000) {		cvportbits |= bits & 0xff; /* Set bits */		DPRINTK("Set bits: %04x\n", bits);	} else {		bits = bits & 0xff;		bits = (~bits) & 0xff;		cvportbits &= bits; /* Clear bits */		DPRINTK("Clear bits: %04x\n", bits);	}	*addr = cvportbits;	DPRINTK("EXIT\n");}/* * Monitor switch on CyberVision board * *  toggle: *    0 = CyberVision Signal *    1 = Amiga Signal *  board = board addr * */inline void cvscreen (int toggle, volatile unsigned char *board){	DPRINTK("ENTER\n");	if (toggle == 1) {		DPRINTK("Show Amiga video\n");		cv64_write_port (0x10, board);	} else {		DPRINTK("Show CyberVision video\n");		cv64_write_port (0x8010, board);	}	DPRINTK("EXIT\n");}/* Control screen display *//* toggle: 0 = on, 1 = off *//* board = registerbase */inline void gfx_on_off(int toggle, volatile unsigned char *regs){	int r;	DPRINTK("ENTER\n");		toggle &= 0x1;	toggle = toggle << 5;	DPRINTK("Turn display %s\n", (toggle ? "off" : "on"));		r = (int) RSeq(regs, SEQ_ID_CLOCKING_MODE);	r &= 0xdf;	/* Set bit 5 to 0 */		WSeq (regs, SEQ_ID_CLOCKING_MODE, r | toggle);	DPRINTK("EXIT\n");}/* * Computes M, N, and R values from * given input frequency. It uses a table of * precomputed values, to keep CPU time low. * * The return value consist of: * lower byte:  Bits 4-0: N Divider Value *	        Bits 5-6: R Value          for e.g. SR10 or SR12 * higher byte: Bits 0-6: M divider value  for e.g. SR11 or SR13 */static unsigned short cv64_compute_clock(unsigned long freq){	static unsigned char *mnr, *save;	/* M, N + R vals */	unsigned long work_freq, r;	unsigned short erg;	long diff, d2;	DPRINTK("ENTER\n");	if (freq < 12500000 || freq > MAXPIXELCLOCK) {		printk("CV64 driver: Illegal clock frequency %ld, using 25MHz\n",		       freq);		freq = 25000000;	}	DPRINTK("Freq = %ld\n", freq);	mnr = clocks;	/* there the vals are stored */	d2 = 0x7fffffff;	while (*mnr) {	/* mnr vals are 0-terminated */		work_freq = (0x37EE * (mnr[0] + 2)) / ((mnr[1] & 0x1F) + 2);		r = (mnr[1] >> 5) & 0x03;		if (r != 0) {			work_freq = work_freq >> r;	/* r is the freq divider */		}		work_freq *= 0x3E8;	/* 2nd part of OSC */		diff = abs(freq - work_freq);		if (d2 >= diff) {			d2 = diff;			/* In save are the vals for minimal diff */			save = mnr;		}		mnr += 2;	}	erg = *((unsigned short *)save);	DPRINTK("EXIT\n");	return (erg);}static int cv_has_4mb (volatile unsigned char *fb){	volatile unsigned long *tr, *tw;	DPRINTK("ENTER\n");	/* write patterns in memory and test if they can be read */	tw = (volatile unsigned long *) fb;	tr = (volatile unsigned long *) (fb + 0x02000000);	*tw = 0x87654321;		if (*tr != 0x87654321) {		DPRINTK("EXIT - <4MB\n");		return (0);	}	/* upper memory region */	tw = (volatile unsigned long *) (fb + 0x00200000);	tr = (volatile unsigned long *) (fb + 0x02200000);	*tw = 0x87654321;	if (*tr != 0x87654321) {		DPRINTK("EXIT - <4MB\n");		return (0);	}	*tw = 0xAAAAAAAA;	if (*tr != 0xAAAAAAAA) {		DPRINTK("EXIT - <4MB\n");		return (0);	}	*tw = 0x55555555;	if (*tr != 0x55555555) {		DPRINTK("EXIT - <4MB\n");		return (0);	}	DPRINTK("EXIT\n");	return (1);}static void cv64_board_init (void){	volatile unsigned char *regs = CyberRegs;	int i;	unsigned int clockpar;	unsigned char test;		DPRINTK("ENTER\n");	/*	 * Special CyberVision 64 board operations	 */	/* Reset board */	for (i = 0; i < 6; i++) {		cv64_write_port (0xff, CyberBase);	}	/* Return to operational mode */	cv64_write_port (0x8004, CyberBase);		/*	 * Generic (?) S3 chip wakeup	 */	/* Disable I/O & memory decoders, video in setup mode */	wb_64 (regs, SREG_VIDEO_SUBS_ENABLE, 0x10);	/* Video responds to cmds, addrs & data */	wb_64 (regs, SREG_OPTION_SELECT, 0x1);	/* Enable I/O & memory decoders, video in operational mode */	wb_64 (regs, SREG_VIDEO_SUBS_ENABLE, 0x8);	/* VGA color emulation, enable cpu access to display mem */ 	wb_64 (regs, GREG_MISC_OUTPUT_W, 0x03);	/* Unlock S3 VGA regs */	WCrt (regs, CRT_ID_REGISTER_LOCK_1, 0x48); 	/* Unlock system control & extension registers */	WCrt (regs, CRT_ID_REGISTER_LOCK_2, 0xA5);/* GRF - Enable interrupts */	/* Enable enhanced regs access, Ready cntl 0 wait states */	test = RCrt (regs, CRT_ID_SYSTEM_CONFIG);	test = test | 0x01;		/* enable enhanced register access */	test = test & 0xEF;		/* clear bit 4, 0 wait state */	WCrt (regs, CRT_ID_SYSTEM_CONFIG, test);	/*	 * bit 0=1: Enable enhaced mode functions	 * bit 2=0: Enhanced mode 8+ bits/pixel	 * bit 4=1: Enable linear addressing	 * bit 5=1: Enable MMIO	 */	wb_64 (regs, ECR_ADV_FUNC_CNTL, 0x31);	/*	 * bit 0=1: Color emulation	 * bit 1=1: Enable CPU access to display memory	 * bit 5=1: Select high 64K memory page	 *//* GRF - 0xE3 */	wb_64 (regs, GREG_MISC_OUTPUT_W, 0x23);		/* Cpu base addr */	WCrt (regs, CRT_ID_EXT_SYS_CNTL_4, 0x0);		/* Reset. This does nothing on Trio, but standard VGA practice */	/* WSeq (CyberRegs, SEQ_ID_RESET, 0x03); */	/* Character clocks 8 dots wide */	WSeq (regs, SEQ_ID_CLOCKING_MODE, 0x01);	/* Enable cpu write to all color planes */	WSeq (regs, SEQ_ID_MAP_MASK, 0x0F);	/* Font table in 1st 8k of plane 2, font A=B disables swtich */	WSeq (regs, SEQ_ID_CHAR_MAP_SELECT, 0x0);	/* Allow mem access to 256kb */	WSeq (regs, SEQ_ID_MEMORY_MODE, 0x2);	/* Unlock S3 extensions to VGA Sequencer regs */	WSeq (regs, SEQ_ID_UNLOCK_EXT, 0x6);		/* Enable 4MB fast page mode */	test = RSeq (regs, SEQ_ID_BUS_REQ_CNTL);	test = test | 1 << 6;	WSeq (regs, SEQ_ID_BUS_REQ_CNTL, test);		/* Faster LUT write: 1 DCLK LUT write cycle, RAMDAC clk doubled */	WSeq (regs, SEQ_ID_RAMDAC_CNTL, 0xC0);	/* Clear immediate clock load bit */	test = RSeq (regs, SEQ_ID_CLKSYN_CNTL_2);	test = test & 0xDF;	/* If > 55MHz, enable 2 cycle memory write */	if (cv64_memclk >= 55000000) {		test |= 0x80;	}	WSeq (regs, SEQ_ID_CLKSYN_CNTL_2, test);	/* Set MCLK value */	clockpar = cv64_compute_clock (cv64_memclk);	test = (clockpar & 0xFF00) >> 8;	WSeq (regs, SEQ_ID_MCLK_HI, test);	test = clockpar & 0xFF;	WSeq (regs, SEQ_ID_MCLK_LO, test);	/* Chip rev specific: Not in my Trio manual!!! */	if (RCrt (regs, CRT_ID_REVISION) == 0x10)		WSeq (regs, SEQ_ID_MORE_MAGIC, test);	/* We now load an 25 MHz, 31kHz, 640x480 standard VGA Mode. */	/* Set DCLK value */	WSeq (regs, SEQ_ID_DCLK_HI, 0x13);	WSeq (regs, SEQ_ID_DCLK_LO, 0x41);	/* Load DCLK (and MCLK?) immediately */	test = RSeq (regs, SEQ_ID_CLKSYN_CNTL_2);	test = test | 0x22;	WSeq (regs, SEQ_ID_CLKSYN_CNTL_2, test);	/* Enable loading of DCLK */	test = rb_64(regs, GREG_MISC_OUTPUT_R);	test = test | 0x0C;	wb_64 (regs, GREG_MISC_OUTPUT_W, test);	/* Turn off immediate xCLK load */	WSeq (regs, SEQ_ID_CLKSYN_CNTL_2, 0x2);	/* Horizontal character clock counts */	/* 8 LSB of 9 bits = total line - 5 */	WCrt (regs, CRT_ID_HOR_TOTAL, 0x5F);	/* Active display line */	WCrt (regs, CRT_ID_HOR_DISP_ENA_END, 0x4F);	/* Blank assertion start */	WCrt (regs, CRT_ID_START_HOR_BLANK, 0x50);	/* Blank assertion end */	WCrt (regs, CRT_ID_END_HOR_BLANK, 0x82);	/* HSYNC assertion start */	WCrt (regs, CRT_ID_START_HOR_RETR, 0x54);	/* HSYNC assertion end */	WCrt (regs, CRT_ID_END_HOR_RETR, 0x80);	WCrt (regs, CRT_ID_VER_TOTAL, 0xBF);	WCrt (regs, CRT_ID_OVERFLOW, 0x1F);	WCrt (regs, CRT_ID_PRESET_ROW_SCAN, 0x0);	WCrt (regs, CRT_ID_MAX_SCAN_LINE, 0x40);	WCrt (regs, CRT_ID_CURSOR_START, 0x00);	WCrt (regs, CRT_ID_CURSOR_END, 0x00);	WCrt (regs, CRT_ID_START_ADDR_HIGH, 0x00);	WCrt (regs, CRT_ID_START_ADDR_LOW, 0x00);	WCrt (regs, CRT_ID_CURSOR_LOC_HIGH, 0x00);	WCrt (regs, CRT_ID_CURSOR_LOC_LOW, 0x00);	WCrt (regs, CRT_ID_START_VER_RETR, 0x9C);	WCrt (regs, CRT_ID_END_VER_RETR, 0x0E);	WCrt (regs, CRT_ID_VER_DISP_ENA_END, 0x8F);	WCrt (regs, CRT_ID_SCREEN_OFFSET, 0x50);	WCrt (regs, CRT_ID_UNDERLINE_LOC, 0x00);	WCrt (regs, CRT_ID_START_VER_BLANK, 0x96);	WCrt (regs, CRT_ID_END_VER_BLANK, 0xB9);	WCrt (regs, CRT_ID_MODE_CONTROL, 0xE3);	WCrt (regs, CRT_ID_LINE_COMPARE, 0xFF);	WCrt (regs, CRT_ID_BACKWAD_COMP_3, 0x10);	/* FIFO enabled */	WCrt (regs, CRT_ID_MISC_1, 0x35);	WCrt (regs, CRT_ID_DISPLAY_FIFO, 0x5A);	WCrt (regs, CRT_ID_EXT_MEM_CNTL_2, 0x70);	WCrt (regs, CRT_ID_LAW_POS_LO, 0x40);	WCrt (regs, CRT_ID_EXT_MEM_CNTL_3, 0xFF);	WGfx (regs, GCT_ID_SET_RESET, 0x0);	WGfx (regs, GCT_ID_ENABLE_SET_RESET, 0x0);	WGfx (regs, GCT_ID_COLOR_COMPARE, 0x0);	WGfx (regs, GCT_ID_DATA_ROTATE, 0x0);	WGfx (regs, GCT_ID_READ_MAP_SELECT, 0x0);	WGfx (regs, GCT_ID_GRAPHICS_MODE, 0x40);	WGfx (regs, GCT_ID_MISC, 0x01);	WGfx (regs, GCT_ID_COLOR_XCARE, 0x0F);	WGfx (regs, GCT_ID_BITMASK, 0xFF);	/* Colors for text mode */	for (i = 0; i < 0xf; i++)		WAttr (regs, i, i);	WAttr (regs, ACT_ID_ATTR_MODE_CNTL, 0x41);	WAttr (regs, ACT_ID_OVERSCAN_COLOR, 0x01);	WAttr (regs, ACT_ID_COLOR_PLANE_ENA, 0x0F);	WAttr (regs, ACT_ID_HOR_PEL_PANNING, 0x0);	WAttr (regs, ACT_ID_COLOR_SELECT, 0x0);	wb_64 (regs, VDAC_MASK, 0xFF);	*((unsigned long *) (regs + ECR_FRGD_COLOR)) = 0xFF;	*((unsigned long *) (regs + ECR_BKGD_COLOR)) = 0;	/* Colors initially set to grayscale */	wb_64 (regs, VDAC_ADDRESS_W, 0);	for (i = 255; i >= 0; i--) {		wb_64(regs, VDAC_DATA, i);		wb_64(regs, VDAC_DATA, i);		wb_64(regs, VDAC_DATA, i);	}	/* GFx hardware cursor off */	WCrt (regs, CRT_ID_HWGC_MODE, 0x00);	/* Set first to 4MB, so test will work */	WCrt (regs, CRT_ID_LAW_CNTL, 0x13);	/* Find "correct" size of fbmem of Z3 board */	if (cv_has_4mb (CyberMem)) {		CyberSize = 1024 * 1024 * 4;		WCrt (regs, CRT_ID_LAW_CNTL, 0x13);		DPRINTK("4MB board\n");	} else {		CyberSize = 1024 * 1024 * 2;		WCrt (regs, CRT_ID_LAW_CNTL, 0x12);		DPRINTK("2MB board\n");	}	/* Initialize graphics engine */	Cyber_WaitBlit();	vgaw16 (regs, ECR_FRGD_MIX, 0x27);	vgaw16 (regs, ECR_BKGD_MIX, 0x07);	vgaw16 (regs, ECR_READ_REG_DATA, 0x1000);	udelay(200);	vgaw16 (regs, ECR_READ_REG_DATA, 0x2000);	Cyber_WaitBlit();	vgaw16 (regs, ECR_READ_REG_DATA, 0x3FFF);	Cyber_WaitBlit();	udelay(200);	vgaw16 (regs, ECR_READ_REG_DATA, 0x4FFF);	Cyber_WaitBlit();	vgaw16 (regs, ECR_BITPLANE_WRITE_MASK, ~0);	Cyber_WaitBlit();	vgaw16 (regs, ECR_READ_REG_DATA, 0xE000);	vgaw16 (regs, ECR_CURRENT_Y_POS2, 0x00);	vgaw16 (regs, ECR_CURRENT_X_POS2, 0x00);	vgaw16 (regs, ECR_READ_REG_DATA, 0xA000);	vgaw16 (regs, ECR_DEST_Y__AX_STEP, 0x00);	vgaw16 (regs, ECR_DEST_Y2__AX_STEP2, 0x00);	vgaw16 (regs, ECR_DEST_X__DIA_STEP, 0x00);	vgaw16 (regs, ECR_DEST_X2__DIA_STEP2, 0x00);	vgaw16 (regs, ECR_SHORT_STROKE, 0x00);	vgaw16 (regs, ECR_DRAW_CMD, 0x01);	Cyber_WaitBlit();	vgaw16 (regs, ECR_READ_REG_DATA, 0x4FFF);	vgaw16 (regs, ECR_BKGD_COLOR, 0x01);	vgaw16 (regs, ECR_FRGD_COLOR, 0x00);	/* Enable video display (set bit 5) *//* ARB - Would also seem to write to AR13. *       May want to use parts of WAttr to set JUST bit 5 */	WAttr (regs, 0x33, 0);	/* GRF - function code ended here */	/* Turn gfx on again */	gfx_on_off (0, regs);	/* Pass-through */	cvscreen (0, CyberBase);	DPRINTK("EXIT\n");}static void cv64_load_video_mode (struct fb_var_screeninfo *video_mode){  volatile unsigned char *regs = CyberRegs;  int fx, fy;  unsigned short mnr;  unsigned short HT, HDE, HBS, HBE, HSS, HSE, VDE, VBS, VBE, VSS, VSE, VT;  char LACE, DBLSCAN, TEXT, CONSOLE;  int cr50, sr15, sr18, clock_mode, test;  int m, n;  int tfillm, temptym;  int hmul;	  /* ---------------- */  int xres, hfront, hsync, hback;  int yres, vfront, vsync, vback;  int bpp;#if 0  float freq_f;#endif  long freq;  /* ---------------- */	  DPRINTK("ENTER\n");  TEXT = 0;	/* if depth == 4 */  CONSOLE = 0;	/* mode num == 255 (console) */  fx = fy = 8;	/* force 8x8 font *//* GRF - Disable interrupts */		  gfx_on_off (1, regs);	  switch (video_mode->bits_per_pixel) {  case 15:  case 16:    hmul = 2;    break;		  default:    hmul = 1;    break;  }	  bpp = video_mode->bits_per_pixel;  xres = video_mode->xres;  hfront = video_mode->right_margin;  hsync = video_mode->hsync_len;  hback = video_mode->left_margin;  LACE = 0;  DBLSCAN = 0;  if (video_mode->vmode & FB_VMODE_DOUBLE) {    yres = video_mode->yres * 2;    vfront = video_mode->lower_margin * 2;    vsync = video_mode->vsync_len * 2;    vback = video_mode->upper_margin * 2;    DBLSCAN = 1;  } else if (video_mode->vmode & FB_VMODE_INTERLACED) {

⌨️ 快捷键说明

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