/* * Example: * setenv videomode video=ctfb:x:800,y:480,depth:16,mode:0,\ * pclk:30066,le:41,ri:89,up:45,lo:12, * hs:1,vs:1,sync:100663296,vmode:0 */ static void s3c_lcd_init(GraphicDevice *panel, struct ctfb_res_modes *mode, int bpp) { uint32_t clk_divider; struct s3c24x0_lcd *regs = s3c24x0_get_base_lcd(); /* Stop the controller. */ clrbits_le32(®s->lcdcon1, 1); /* Calculate clock divider. */ clk_divider = (get_HCLK() / PS2KHZ(mode->pixclock)) / 1000; clk_divider = DIV_ROUND_UP(clk_divider, 2); if (clk_divider) clk_divider -= 1; /* Program LCD configuration. */ switch (bpp) { case 16: writel(S3CFB_LCDCON1_BPPMODE_TFT_16BPP | S3CFB_LCDCON1_PNRMODE_TFT | S3CFB_LCDCON1_CLKVAL(clk_divider), ®s->lcdcon1); writel(S3CFB_LCDCON5_HWSWP | S3CFB_LCDCON5_FRM565, ®s->lcdcon5); break; case 24: writel(S3CFB_LCDCON1_BPPMODE_TFT_24BPP | S3CFB_LCDCON1_PNRMODE_TFT | S3CFB_LCDCON1_CLKVAL(clk_divider), ®s->lcdcon1); writel(S3CFB_LCDCON5_BPP24BL, ®s->lcdcon5); break; } writel(S3CFB_LCDCON2_LINEVAL(mode->yres - 1) | S3CFB_LCDCON2_VBPD(mode->upper_margin - 1) | S3CFB_LCDCON2_VFPD(mode->lower_margin - 1) | S3CFB_LCDCON2_VSPW(mode->vsync_len - 1), ®s->lcdcon2); writel(S3CFB_LCDCON3_HBPD(mode->right_margin - 1) | S3CFB_LCDCON3_HFPD(mode->left_margin - 1) | S3CFB_LCDCON3_HOZVAL(mode->xres - 1), ®s->lcdcon3); writel(S3CFB_LCDCON4_HSPW(mode->hsync_len - 1), ®s->lcdcon4); /* Write FB address. */ writel(panel->frameAdrs >> 1, ®s->lcdsaddr1); writel((panel->frameAdrs + (mode->xres * mode->yres * panel->gdfBytesPP)) >> 1, ®s->lcdsaddr2); writel(mode->xres * bpp / 16, ®s->lcdsaddr3); /* Start the controller. */ setbits_le32(®s->lcdcon1, 1); }
void board_video_init(GraphicDevice *pGD) { struct s3c24x0_lcd * const lcd = s3c24x0_get_base_lcd(); struct s3c2410_nand * const nand = s3c2410_get_base_nand(); lcd->LCDCON1 = 0x00000378; /* CLKVAL=4, BPPMODE=16bpp, TFT, ENVID=0 */ lcd->LCDCON2 = (VBPD_320240<<24)|(LINEVAL_TFT_320240<<14)|(VFPD_320240<<6)|(VSPW_320240); lcd->LCDCON3 = (HBPD_320240<<19)|(HOZVAL_TFT_320240<<8)|(HFPD_320240); lcd->LCDCON4 = (MVAL<<8)|(HSPW_320240); lcd->LCDCON5 = 0x00000f09; lcd->LPCSEL = 0x00000000; }
/******************************************************************************* * * Init video chip with common Linux graphic modes (lilo) */ void *video_hw_init (void) { struct s3c24x0_lcd * const lcd = s3c24x0_get_base_lcd(); GraphicDevice *pGD = (GraphicDevice *)&smi; int videomode; unsigned long t1, hsynch, vsynch; char *penv; int tmp, i, bits_per_pixel; struct ctfb_res_modes *res_mode; struct ctfb_res_modes var_mode; // unsigned char videoout; /* Search for video chip */ // printf("Video: "); //by mickeyos tmp = 0; videomode = CFG_SYS_DEFAULT_VIDEO_MODE; /* get video mode via environment */ if ((penv = getenv ("videomode")) != NULL) { /* deceide if it is a string */ if (penv[0] <= '9') { videomode = (int) simple_strtoul (penv, NULL, 16); tmp = 1; } } else { tmp = 1; } if (tmp) { /* parameter are vesa modes */ /* search params */ for (i = 0; i < VESA_MODES_COUNT; i++) { if (vesa_modes[i].vesanr == videomode) break; } if (i == VESA_MODES_COUNT) { printf ("no VESA Mode found, switching to mode 0x%x ", CFG_SYS_DEFAULT_VIDEO_MODE); i = 0; } res_mode = (struct ctfb_res_modes *) &res_mode_init[vesa_modes[i]. resindex]; bits_per_pixel = vesa_modes[i].bits_per_pixel; } else { res_mode = (struct ctfb_res_modes *) &var_mode; bits_per_pixel = video_get_params (res_mode, penv); } /* calculate hsynch and vsynch freq (info only) */ t1 = (res_mode->left_margin + res_mode->xres + res_mode->right_margin + res_mode->hsync_len) / 8; t1 *= 8; t1 *= res_mode->pixclock; t1 /= 1000; hsynch = 1000000000L / t1; t1 *= (res_mode->upper_margin + res_mode->yres + res_mode->lower_margin + res_mode->vsync_len); t1 /= 1000; vsynch = 1000000000L / t1; /* fill in Graphic device struct */ sprintf (pGD->modeIdent, "%dx%dx%d %ldkHz %ldHz", res_mode->xres, res_mode->yres, bits_per_pixel, (hsynch / 1000), (vsynch / 1000)); // printf ("%s\n", pGD->modeIdent); //by mickeyos pGD->winSizeX = res_mode->xres; pGD->winSizeY = res_mode->yres; pGD->plnSizeX = res_mode->xres; pGD->plnSizeY = res_mode->yres; switch (bits_per_pixel) { case 8: pGD->gdfBytesPP = 1; pGD->gdfIndex = GDF__8BIT_INDEX; break; case 15: pGD->gdfBytesPP = 2; pGD->gdfIndex = GDF_15BIT_555RGB; break; case 16: pGD->gdfBytesPP = 2; pGD->gdfIndex = GDF_16BIT_565RGB; break; case 24: pGD->gdfBytesPP = 3; pGD->gdfIndex = GDF_24BIT_888RGB; break; } /* statically configure settings */ pGD->winSizeX = pGD->plnSizeX = 320; pGD->winSizeY = pGD->plnSizeY = 240; pGD->gdfBytesPP = 2; pGD->gdfIndex = GDF_16BIT_565RGB; pGD->frameAdrs = LCD_VIDEO_ADDR; pGD->memSize = VIDEO_MEM_SIZE; board_video_init(pGD); writel((pGD->frameAdrs >> 1), &lcd->LCDSADDR1); /* This marks the end of the frame buffer. */ writel((((readl(&lcd->LCDSADDR1))&0x1fffff) + (pGD->winSizeX+0) * pGD->winSizeY), &lcd->LCDSADDR2); writel((pGD->winSizeX & 0x7ff), &lcd->LCDSADDR3); /* Clear video memory */ memset((void *)pGD->frameAdrs, 0, pGD->memSize); /* Enable Display */ writel((readl(&lcd->LCDCON1) | 0x01), & lcd->LCDCON1); /* ENVID = 1 */ return ((void*)&smi); }