lcd.c驅(qū)動源碼:
#include "linux/module.h"
#include "linux/kernel.h"
#include "linux/errno.h"
#include "linux/string.h"
#include "linux/mm.h"
#include "linux/slab.h"
#include "linux/vmalloc.h"
#include "linux/delay.h"
#include "linux/interrupt.h"
#include "asm/uaccess.h"
#include "linux/fb.h"
#include "linux/init.h"
#include "linux/clk.h"
#include "linux/dma-mapping.h"
static struct fb_info *s3c_lcd_info;
static u32 s3c_pseudo_palette[16];
static volatile unsigned long *gpbcon;
static volatile unsigned long *gpbdat;
static volatile unsigned long *gpfcon;
static volatile unsigned long *gpfdat;
static volatile unsigned long *gpicon;
static volatile unsigned long *gpjcon;
static volatile unsigned long *mifpcon;
static volatile unsigned long *spcon;
struct s3c6410_lcd_regs {
unsigned long vidcon0;
unsigned long vidcon1;
unsigned long vidcon2;
unsigned long reserver1;
unsigned long vidtcon0;
unsigned long vidtcon1;
unsigned long vidtcon2;
unsigned long reserver2;
unsigned long wincon0;
unsigned long wincon1;
unsigned long wincon2;
unsigned long wincon3;
unsigned long wincon4;
unsigned long reserver3[3];
unsigned long vidosd0a;
unsigned long vidosd0b;
unsigned long vidosd0c;
unsigned long reserver4;
unsigned long vidosd1a;
unsigned long vidosd1b;
unsigned long vidosd1c;
unsigned long vidosd1d;
unsigned long vidosd2a;
unsigned long vidosd2b;
unsigned long vidosd2c;
unsigned long vidosd2d;
unsigned long vidosd3a;
unsigned long vidosd3b;
unsigned long vidosd3c;
unsigned long reserver5;
unsigned long vidosd4a;
unsigned long vidosd4b;
unsigned long vidosd4c;
unsigned long reserver6[5];
unsigned long vidw00add0b0;
unsigned long vidw00add0b1;
unsigned long vidw01add0b0;
unsigned long vidw01add0b1;
unsigned long vidw02add0;
unsigned long reserver7;
unsigned long vidw03add0;
unsigned long reserver8;
unsigned long vidw04add0;
unsigned long reserver9[3];
unsigned long vidw00add1b0;
unsigned long vidw00add1b1;
};
static inline unsigned int chan_to_field(unsigned int chan, struct fb_bitfield *bf)
{
chan &= 0xffff;
chan >>= 16 - bf->length;
return chan << bf->offset;
}
static int s3c_fb_setcolreg(unsigned int regno, unsigned int red,
unsigned int green, unsigned int blue,
unsigned int transp, struct fb_info *info)
{
unsigned int val;
if (regno > 16)
return 1;
u32 *pal = info->pseudo_palette;
// 用red,green,blue三原色構(gòu)造出val
val = chan_to_field(red, &info->var.red);
val |= chan_to_field(green, &info->var.green);
val |= chan_to_field(blue, &info->var.blue);
pal[regno] = val;
return 0;
}
static struct fb_ops s3c_fb_ops = {
.owner = THIS_MODULE,
.fb_setcolreg = s3c_fb_setcolreg,
.fb_fillrect = cfb_fillrect,
.fb_copyarea = cfb_copyarea,
.fb_imageblit = cfb_imageblit,
};
static struct s3c6410_lcd_regs * lcd_regs;
static int s3c_lcd_init(void)
{
struct clk *clk;
int hclk;
int clkval;
// 1. 分配fb_info
s3c_lcd_info = framebuffer_alloc(0, NULL);
// 2. 設(shè)置
// 2.1 設(shè)置固定的信息
strcpy(s3c_lcd_info->fix.id, "uplooking_lcd");
s3c_lcd_info->fix.smem_len = 480*272*2;
s3c_lcd_info->fix.type = FB_TYPE_PACKED_PIXELS;
s3c_lcd_info->fix.visual = FB_VISUAL_TRUECOLOR;
s3c_lcd_info->fix.line_length = 480*2;
// 2.2 設(shè)置可變的信息
s3c_lcd_info->var.xres = 480; //分辨率
s3c_lcd_info->var.yres = 272;
s3c_lcd_info->var.xres_virtual = 480; //虛擬分辨率
s3c_lcd_info->var.yres_virtual = 272;
s3c_lcd_info->var.bits_per_pixel = 16;
s3c_lcd_info->var.red.length = 5;
s3c_lcd_info->var.red.offset = 11;
s3c_lcd_info->var.green.length = 6;
s3c_lcd_info->var.green.offset = 5;
s3c_lcd_info->var.blue.length = 5;
s3c_lcd_info->var.blue.offset = 0;
s3c_lcd_info->var.activate = FB_ACTIVATE_NOW;
// 2.3 設(shè)置操作函數(shù)
s3c_lcd_info->fbops = &s3c_fb_ops;
// 2.4 設(shè)置其他信息
//s3c_lcd_info->screen_base = ; // 顯存的虛擬地址
s3c_lcd_info->screen_size = 480*272*2;
s3c_lcd_info->pseudo_palette = &s3c_pseudo_palette;
// 4. 硬件相關(guān)的操作
// 4.1 配置GPIO用于LCD
gpicon = ioremap(0x7F008100, 4);
*gpicon = 0xAAAAAAAA;
gpjcon = ioremap(0x7F008120, 4);
*gpjcon = 0xAAAAAAAA;
gpbcon = ioremap(0x7F008020, 4);
gpbdat = gpbcon + 1;
gpfcon = ioremap(0x7F0080A0, 4);
gpfdat = gpfcon + 1;
// 4.2 根據(jù)LCD的性能設(shè)置LCD控制器
// MIFPCON
mifpcon = ioremap(0x7410800C, 4);
*mifpcon &= ~(1<<3);
spcon = ioremap(0x7F0081A0, 4);
*spcon &= ~(3);
*spcon |= 1;
lcd_regs = ioremap(0x77100000, sizeof(struct s3c6410_lcd_regs));
clk = clk_get(NULL, "lcd");
clk_enable(clk); // HCLK_GATE[3]設(shè)為1
// HCLK_GATE = ioremap(0x7E00F030, 4);
// *HCLK_GATE |= (1<<3);
// bit[13:6], CLKVAL_F,VCLK = Video Clock Source / (CLKVAL+1)
// VCLK = 9000000
// CLKVAL_F = hclk/9000000 - 1
// bit[3:2], CLKSEL_F, 00 = HCLK
// bit[1], ENVID-使能LCD控制器的輸出, 先設(shè)為0, 最后全部設(shè)置好了再設(shè)為1
clk = clk_get(NULL, "hclk");
hclk = clk_get_rate(clk);
clkval = hclk/9000000 - 1;
printk(KERN_INFO "hclk = %d, clkval = %d\n", hclk, clkval);
lcd_regs->vidcon0 = (0<<29)|(0<<26) | (0<<17) | (clkval << 6) | (1<<4);
// bit[7], 0-在VLCK下降沿讀數(shù)據(jù)
// bit[6], HSYNC低脈沖有效
// bit[5], VSYNC低脈沖有效
// bit[4], VDEN高電平有效
lcd_regs->vidcon1 = (0<<7) | (1<<6) | (1<<5) | (0<<4);
// LCD手冊P11
// tvp = 10, tvb = 2, tvf=2
lcd_regs->vidtcon0 = (2<<16) | (2<<8) | (10<<0); //修改了 都加1
// LCD手冊P11
// thp = 41, thb = 2, thf=2
lcd_regs->vidtcon1 = (1<<16) | (1<<8) | (40<<0);
lcd_regs->vidtcon2 = (271<<11) | (479<<0);
// 4.3 分配顯存, 并告訴LCD控制器
s3c_lcd_info->screen_base = dma_alloc_writecombine(NULL, s3c_lcd_info->screen_size,
&s3c_lcd_info->fix.smem_start, GFP_KERNEL);
// bit[17],BSWP = 0, bit[16],HWSWP = 0
// bit[5:2],BPPMODE_F, 0b1011, 24bpp
// bit[0], ENWIN_F, 0-先不使能
lcd_regs->wincon0 &= ~(0xf << 2);
//lcd_regs->wincon0 |= (0xb<<2); // unpacked 24 BPP (non-palletized R:8-G:8-B:8 )
lcd_regs->wincon0 |= (0x5<<2);
#define LeftTopX 0
#define LeftTopY 0
#define RightBotX 479
#define RightBotY 271
lcd_regs->vidosd0a = (LeftTopX<<11) | (LeftTopY << 0);
lcd_regs->vidosd0b = (RightBotX<<11) | (RightBotY << 0);
//lcd_regs->vidosd0c = 480*272/2;
lcd_regs->vidosd0c = 480*272;
lcd_regs->vidw00add0b0 = s3c_lcd_info->fix.smem_start;
lcd_regs->vidw00add1b0 = (s3c_lcd_info->fix.smem_start + s3c_lcd_info->fix.smem_len) & 0xffffff;
// 4.4 使能
lcd_regs->vidcon0 |= (3); // 使能LCD控制器輸出信號
lcd_regs->wincon0 |= (1<<0); // 使能窗口0
// 3. 注冊
register_framebuffer(s3c_lcd_info);
return 0;
}
static void s3c_lcd_exit(void)
{
struct clk *clk;
unregister_framebuffer(s3c_lcd_info);
lcd_regs->vidcon0 &= ~(1<<1); // 禁止LCD控制器輸出信號
lcd_regs->wincon0 &= ~(1<<0); // 禁止窗口0
dma_free_writecombine(NULL, s3c_lcd_info->screen_size, s3c_lcd_info->screen_base,
s3c_lcd_info->fix.smem_start);
clk = clk_get(NULL, "lcd");
clk_disable(clk); // HCLK_GATE[3]設(shè)為0
iounmap(lcd_regs);
iounmap(gpbcon);
iounmap(gpfcon);
iounmap(gpicon);
iounmap(gpjcon);
iounmap(mifpcon);
iounmap(spcon);
framebuffer_release(s3c_lcd_info);
}
module_init(s3c_lcd_init);
module_exit(s3c_lcd_exit);
MODULE_LICENSE("GPL");
====================================================================
Makefile文件:
KERN_DIR = /home/linux/linux-3.0.1
all:
make -C $(KERN_DIR) M=`pwd` modules
clean:
make -C $(KERN_DIR) M=`pwd` modules clean
rm -rf modules.order
obj-m += lcd.o
==================================================================
LCD實(shí)驗(yàn):
想在6410的驅(qū)動上面的測試自己的驅(qū)動首先要卸載開發(fā)板的官方驅(qū)動:
1、make menuconfig去掉內(nèi)核自帶的LCD驅(qū)動
在Device Drivers=>Graphics support=>S3C Framebuffer Support
和
Device Drivers=>Multimedia support=>Video For Linux
這兩項(xiàng)要去掉!
默認(rèn):
->Device Drivers
[*] Multimedia support --->
[*] Video For Linux
->Graphics support
[*] S3C Framebuffer Support (eXtended)
Select LCD Type (4.3 inch 480x272 TFT LCD) --->
(X) 4.3 inch 480x272 TFT LCD
[*] Advanced options for S3C Framebuffer
Select BPP(Bits Per Pixel) (16 BPP) --->
(X) 16 BPP
(4) Number of Framebuffers
[*] Enable Virtual Screen
[*] Enable Double Buffering
改為:
->Device Drivers
[*] Multimedia support --->
[ ] Video For Linux
->Graphics support
[ ] S3C Framebuffer Support (eXtended)
[*] Support for frame buffer devices ---> //為了編譯出要用的模塊
[M] Samsung S3C Framebuffer Support
2、上面是去除自帶的驅(qū)動支持,還要在arch\arm\mach-s3c64xx\mach-smdk6410.c和
change\mach-smdk6410.c這兩個(gè)文件中相應(yīng)的結(jié)構(gòu)體注釋掉:
s3c_device_vpp
s3c_device_mfc
s3c_device_tvenc
s3c_device_tvscaler
s3c_device_rotator
s3c_device_jpeg
s3c_device_g2d
s3c_device_g3d
這樣子 就可以通過編譯了:
make zImage //生成內(nèi)核鏡像文件
make modules
cp arch/arm/boot/zImage ../../zImage_no_lcd
然后把/drivers/video中的cfbcopyarea.ko 、cfbfillrect.ko 、cfbimgblt.ko 加載到開發(fā)板:
cp drivers/video/cfbcopyarea.ko drivers/video/cfbfillrect.ko drivers/video/cfbimgblt.ko ../../../fs_ok6410_yaffs2/driver/
3、把開發(fā)板設(shè)置為SD卡啟動,使用SD卡啟動后按空格進(jìn)入SD卡的u-boot;
4、用SD卡里面的u-boot燒寫內(nèi)核到0x000000200000-0x000000700000 : "Kernel"分區(qū):
tftp 50008000 zImage_no_lcd
nand erase 200000 500000
nand write 50008000 200000 500000
5、燒寫完成后設(shè)置開發(fā)版為nand flash啟動,使用新內(nèi)核啟動。
6、測試1:
重啟開發(fā)板,然后執(zhí)行以下命令
insmod cfbcopyarea.ko
insmod cfbfillrect.ko
insmod cfbimgblt.ko
insmod lcd.ko
echo hello > /dev/tty1
可以看到屏幕打印了文字hello
cat lcd.ko > /dev/fb0
可以看到花屏了
測試2:
在開發(fā)板的文件系統(tǒng)的/etc/inittab文件中添加一行tty1::askfirst:-/bin/sh
重啟開發(fā)板,然后執(zhí)行以下命令
insmod cfbcopyarea.ko
insmod cfbfillrect.ko
insmod cfbimgblt.ko
insmod lcd.ko
可以看到有文字在屏幕上顯示,再裝載我們之前做的輸入子系統(tǒng)的按鍵驅(qū)動
insmod button_input.ko
就可以在開發(fā)板屏幕上看到shell命令行了
上一篇:OK6410觸摸屏驅(qū)動
下一篇:OK6410之nand flash塊設(shè)備驅(qū)動
推薦閱讀
史海拾趣
在技術(shù)創(chuàng)新的基礎(chǔ)上,CONTTEK Group GmbH公司開始積極拓展市場。公司不僅在國內(nèi)市場取得了良好的銷售業(yè)績,還積極開拓國際市場,與多家國際知名企業(yè)建立了合作關(guān)系。通過參加國際展覽、建立海外銷售網(wǎng)絡(luò)等方式,公司的品牌影響力逐漸提升,產(chǎn)品也遠(yuǎn)銷至全球各地。
隨著市場競爭的加劇,CONTTEK Group GmbH公司意識到只有不斷創(chuàng)新才能在行業(yè)中立足。因此,公司加大了對研發(fā)的投入,積極引進(jìn)新技術(shù)、新材料和新工藝,不斷推動產(chǎn)品的升級換代。通過持續(xù)的技術(shù)創(chuàng)新,公司成功推出了一系列具有創(chuàng)新性和競爭力的新產(chǎn)品,進(jìn)一步鞏固了其在電子連接器領(lǐng)域的領(lǐng)先地位。
為了擴(kuò)大市場份額,Densitron公司制定了一系列市場拓展策略。公司首先分析了市場需求和競爭態(tài)勢,確定了目標(biāo)市場。然后,通過加強(qiáng)品牌宣傳、優(yōu)化銷售渠道、提高客戶服務(wù)質(zhì)量等手段,不斷提升品牌知名度和客戶滿意度。此外,公司還積極開展國際合作,與全球知名電子企業(yè)建立了緊密的合作關(guān)系,共同開拓市場。這些策略的實(shí)施,使得Densitron公司的市場份額逐年上升,成為行業(yè)內(nèi)的領(lǐng)軍企業(yè)。
隨著電子行業(yè)的快速發(fā)展,新技術(shù)、新產(chǎn)品層出不窮,給傳統(tǒng)企業(yè)帶來了巨大的挑戰(zhàn)。面對這種情況,Densitron公司積極應(yīng)對變革,不斷調(diào)整自身的戰(zhàn)略和業(yè)務(wù)模式。公司加大了對新技術(shù)、新產(chǎn)品的研發(fā)投入,緊跟行業(yè)趨勢。同時(shí),通過優(yōu)化生產(chǎn)流程、提高生產(chǎn)效率、降低生產(chǎn)成本等手段,不斷提升自身的競爭力。這些努力使得Densitron公司能夠在變革中保持領(lǐng)先地位。
AINFO Inc公司在追求經(jīng)濟(jì)效益的同時(shí),也積極履行社會責(zé)任,關(guān)注可持續(xù)發(fā)展。公司注重環(huán)境保護(hù)和資源節(jié)約,通過采用環(huán)保材料和節(jié)能技術(shù),降低了生產(chǎn)過程中的能耗和排放。同時(shí),公司也積極參與公益事業(yè),為社會做出了積極貢獻(xiàn)。
請注意,以上故事僅為框架性的描述,并非AINFO Inc公司的實(shí)際發(fā)展歷程。如果您需要了解該公司的具體發(fā)展情況,建議查閱相關(guān)資料或訪問其官方網(wǎng)站。
目錄 第一章 電子測量的自動化 第二章 自動測試用計(jì)算機(jī) 第三章 自動測試用計(jì)算機(jī)軟件 第四章 標(biāo)準(zhǔn)接口系統(tǒng) 第五章 測量儀器的程控化 第六章 采用微處理器的自動測試儀器 第七章 自動測試系統(tǒng) 第八章 自動測試設(shè)備的故障診斷… 查看全部問答∨ |
|
轉(zhuǎn):公布一個(gè)ARM免費(fèi)實(shí)戰(zhàn)項(xiàng)目的活動 公布一個(gè)ARM免費(fèi)實(shí)戰(zhàn)項(xiàng)目開發(fā)計(jì)劃 ARM免費(fèi)實(shí)戰(zhàn):Mp3播放器項(xiàng)目開發(fā)計(jì)劃 (重新使用基于ARM的STM32完整實(shí)現(xiàn)) 從0到軟硬件精通的實(shí)戰(zhàn)項(xiàng)目技術(shù)方案已經(jīng)完成,分工正式開始了,要參與的趕快啊 產(chǎn)品做出來后,論壇有詳細(xì)充足的細(xì)節(jié)資料 ...… 查看全部問答∨ |
|
我是一個(gè)草根大學(xué)的本科畢業(yè)生,專業(yè)是計(jì)科,考研沒考上,想?yún)⒓忧度胧脚嘤?xùn),問問各位高手嵌入式式培訓(xùn)哪個(gè)好,看了尚觀,華清,和亞嵌,不知道哪個(gè)好?… 查看全部問答∨ |
|
用STM32MSD例程帶TF卡做u盤,你們讀寫速度能到多少? 我的用48M主頻,速度不到200K字節(jié)每秒。 有什么辦法改進(jìn)速度?usb端點(diǎn)雙緩沖?增加TF讀寫緩沖區(qū)? 你們測過速度嗎? 我用2M的pdf文件測得。… 查看全部問答∨ |
我昨天重裝了次系統(tǒng),后來發(fā)現(xiàn)CCS不能用,于是直接刪掉了TI 問價(jià)夾, 再裝上CCS2.2 后,啟動CCS2.2 后就彈出 error reading coder composer setup information.coder composer may not have been correctly installed 這是什么原因啊 和裝的 ...… 查看全部問答∨ |
設(shè)計(jì)資源 培訓(xùn) 開發(fā)板 精華推薦
- 基于GPS自動授時(shí)的無線智能控制器的設(shè)計(jì)
- 基于PTR2000的無線氣象信息采集系統(tǒng)設(shè)計(jì)
- Microchip推出MEC175xB系列器件,為嵌入式控制器引入硬件 抗量子攻擊能力
- 無人飛行器機(jī)載穩(wěn)定云臺控制系統(tǒng)的設(shè)計(jì)
- 匠芯創(chuàng)推出面向具身智能高性能實(shí)時(shí)處理器M7000
- 基于HW2181B的航模無線遙控通信系統(tǒng)設(shè)計(jì)與實(shí)現(xiàn)
- 應(yīng)對機(jī)器人“四高”,極海推出全球首款雙核Cortex-M52 MCU G32R501
- 非道路移動機(jī)械透射式煙度計(jì)研究與實(shí)現(xiàn)
- 基于STM32F103的角磨機(jī)開關(guān)磁阻電機(jī)控制器的設(shè)計(jì)
- 大眾汽車宣布明年起其所有電動車型全面轉(zhuǎn)向磷酸鐵鋰電池,升級至MEB Plus平臺
- 總產(chǎn)值破2000億,深圳要做“機(jī)器人第一城”?
- 鴻道Intewell操作系統(tǒng) 人形機(jī)器人底層操作系統(tǒng)
- 如何定位國產(chǎn)智駕芯片的終局價(jià)值?
- 新一代車規(guī)級數(shù)字功放電感VSAD-T系列 為汽車音響注入高保真基因
- 蜂巢能源快充電池突破:15分鐘充至滿電,提升30%效率
- 整車操作系統(tǒng)何以躋身智能汽車三大件?
- 人形機(jī)器人如何做到“手眼”協(xié)同+“大小腦”協(xié)同?
- 中國電池公司獲英國政府10億英鎊支持!
- 從游戲到智能駕駛,英偉達(dá)有哪些技術(shù)升級?
- 預(yù)報(bào)名有獎(jiǎng)直播:煮酒數(shù)創(chuàng)客,看如何讓好創(chuàng)意發(fā)生!
- 觀看安森美半導(dǎo)體高靈敏度觸摸傳感器應(yīng)用視頻,輕松答題贏好禮!
- 有獎(jiǎng)直播|TI毫米波雷達(dá)在汽車領(lǐng)域的最新應(yīng)用
- MicroPython搶鮮玩 Python遇上MCU=? 由你定
- 大聯(lián)大世平集團(tuán)有獎(jiǎng)直播:最新功能安全牽引逆變器方案:助力汽車提升續(xù)航與節(jié)省成本!預(yù)約有禮
- ADI 全新中文資料(2019 年 11 月)
- 一鍵獲取【TI 五大工業(yè)參考設(shè)計(jì) FAQ】