一。显示效果:
二。驱动:
/*********************************
** LCD 驱动程序 **
*********************************/
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
//#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
//#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#define DEVICE_NAME "tft_tb35_micro2440_drv"
//寄存器定义
static void __iomem *base_addr;
static void __iomem *base_addr1;
static void __iomem *base_addr2;
static void __iomem *base_addr3;
static void __iomem *base_addr4;
#define LCDCON1_MICRO2440 (*(volatile unsigned long *)(base_addr 0)) //LCD控制1寄存器
#define LCDCON2_MICRO2440 (*(volatile unsigned long *)(base_addr 4)) //LCD控制2寄存器
#define LCDCON3_MICRO2440 (*(volatile unsigned long *)(base_addr 8)) //LCD控制3寄存器
#define LCDCON4_MICRO2440 (*(volatile unsigned long *)(base_addr 0x0c))//LCD控制4寄存器
#define LCDCON5_MICRO2440 (*(volatile unsigned long *)(base_addr 0x10))//LCD控制5寄存器
#define LCDSADDR1_MICRO2440 (*(volatile unsigned long *)(base_addr 0x14))//帧缓冲器开始地址1寄存器
#define LCDSADDR2_MICRO2440 (*(volatile unsigned long *)(base_addr 0x18))//帧缓冲器开始地址2寄存器
#define LCDSADDR3_MICRO2440 (*(volatile unsigned long *)(base_addr 0x1c))//帧缓冲器开始地址3寄存器
#define REDLUT_MICRO2440 (*(volatile unsigned long *)(base_addr 0x20))//红色查找表寄存器
#define GREENLUT_MICRO2440 (*(volatile unsigned long *)(base_addr 0x24))//绿色查找表寄存器
#define BLUELUT_MICRO2440 (*(volatile unsigned long *)(base_addr 0x28))//蓝色查找表寄存器
#define DITHMODE_MICRO2440 (*(volatile unsigned long *)(base_addr1 0)) //抖动模式寄存器
#define TPAL_MICRO2440 (*(volatile unsigned long *)(base_addr1 0x04))//临时调色板寄存器
#define LCDINTPND_MICRO2440 (*(volatile unsigned long *)(base_addr1 0x08))//LCD中断挂起寄存器
#define LCDSRCPND_MICRO2440 (*(volatile unsigned long *)(base_addr1 0x0c))//LCD源挂起寄存器
#define LCDINTMSK_MICRO2440 (*(volatile unsigned long *)(base_addr1 0x10))//LCD中断屏蔽寄存器
#define TCONSEL_MICRO2440 (*(volatile unsigned long *)(base_addr1 0x14))//TCON控制寄存器
#define GPCCON_MICRO2440 (*(volatile unsigned long *)(base_addr2 0))
#define GPCDAT_MICRO2440 (*(volatile unsigned long *)(base_addr2 0x04))
#define GPCUP_MICRO2440 (*(volatile unsigned long *)(base_addr2 0x08))
#define GPDCON_MICRO2440 (*(volatile unsigned long *)(base_addr2 0x10))
#define GPDDAT_MICRO2440 (*(volatile unsigned long *)(base_addr2 0x14))
#define GPDUP_MICRO2440 (*(volatile unsigned long *)(base_addr2 0x18))
#define GPGCON_MICRO2440 (*(volatile unsigned long *)(base_addr3 0))
#define GPGDAT_MICRO2440 (*(volatile unsigned long *)(base_addr3 4))
#define GPGUP_MICRO2440 (*(volatile unsigned long *)(base_addr3 8))
#define LCD_BUFFER_ADDRESS (*(volatile unsigned long *)(base_addr4 0))
#define LOWER21BITS(n) ((n)&0x1fffff)
#define BPPMODE_1BPP 0x08
#define BPPMODE_2BPP 0x09
#define BPPMODE_4BPP 0x0a
#define BPPMODE_8BPP 0x0b
#define BPPMODE_16BPP 0x0c
#define BPPMODE_24BPP 0x0d
#define LCDTYPE_TFT 0x03
#define ENVID_DISABLE 0
#define ENVID_ENABLE 1
#define FORMAT8BPP_5551 0
#define FORMAT8BPP_565 1
#define HSYNC_NORM 0
#define HSYNC_INV 1
#define VSYNC_NORM 0
#define VSYNC_INV 1
#define BSWP 1
#define HWSWP 1
//TFT LCD PANEL(240*320)
#define MODE_TFT_1BIT_240320 (0x4101)
#define MODE_TFT_8BIT_240320 (0x4102)
#define MODE_TFT_16BIT_240320 (0x4104)
#define MODE_TFT_24BIT_240320 (0x4108)
//TFT240320
#define LCD_XSIZE_TFT_240320 (240)
#define LCD_YSIZE_TFT_240320 (320)
#define HOZVAL_TFT_240320 (LCD_XSIZE_TFT_240320-1)
#define LINEVAL_TFT_240320 (LCD_YSIZE_TFT_240320-1)
#define CLKVAL_TFT_240320 (7)
#define VBPD_240320 1
#define VFPD_240320 2
#define VSPW_240320 1
#define HBPD_240320 19
#define HFPD_240320 10
#define HSPW_240320 10
//#define LCDFRAMEBUFFER 0x30400000
unsigned long fb_base_addr;
unsigned int bpp;
unsigned int xsize;
unsigned int ysize;
unsigned long lcd_buffer_base_addr;
unsigned long phyaddr;
static struct semaphore lock;
static struct clk *tft_clock;
unsigned long hclk;
struct page *data_temp;
unsigned long address;
static volatile unsigned long pointer=0;
static void tft_tb35_init(void)
{
unsigned char red,green,blue;
unsigned short *addr;
unsigned int i,j;
//IO映射
base_addr=ioremap(0x4d000000,0x30);
base_addr1=ioremap(0x4d00004c,0x16);
base_addr2=ioremap(0x56000020,0x20);
base_addr3=ioremap(0x56000060,0x20);
//获取时钟
tft_clock = clk_get(NULL, "hclk");//获取PCLK
clk_enable(tft_clock);
hclk= clk_get_rate(tft_clock);
//设置IO口
GPCUP_MICRO2440=0xffffffff;
GPDUP_MICRO2440=0xffffffff;
GPCCON_MICRO2440=0xaaaaaaaa;
GPDCON_MICRO2440=0xaaaaaaaa;
GPGCON_MICRO2440=(GPGCON_MICRO2440&(~(3<<8)))|(3<<8);
GPGUP_MICRO2440=(GPGUP_MICRO2440&(~(1<<4)))|(1<<4);
//LCD初始化
LCDCON1_MICRO2440=(CLKVAL_TFT_240320<<8)|(LCDTYPE_TFT<<5)|(BPPMODE_16BPP<<1)|(ENVID_DISABLE<<0);
LCDCON2_MICRO2440=(VBPD_240320<<24)|(LINEVAL_TFT_240320<<14)|(VFPD_240320<<6)|(VSPW_240320);
LCDCON3_MICRO2440=(HBPD_240320<<19)|(HOZVAL_TFT_240320<<8)|(HFPD_240320);
LCDCON4_MICRO2440=HSPW_240320;
LCDCON5_MICRO2440=(FORMAT8BPP_565<<11)|(HSYNC_INV<<9)|(VSYNC_INV<<8)|(HWSWP<<1);
LCDCON5_MICRO2440=(LCDCON5_MICRO2440&(~(1<<5)))|(0<<5);
LCDCON5_MICRO2440=(LCDCON5_MICRO2440&(~(1<<3)))|(1<<3);
//申请连续物理地址
data_temp=alloc_pages(GFP_KERNEL,9);
lcd_buffer_base_addr=(unsigned long)page_address(data_temp);//返回的为虚拟地址
//定义LCD显存
phyaddr=virt_to_phys(lcd_buffer_base_addr);//将返回的虚拟地址换算成物理地址然后赋值给帧缓冲寄存器
LCDSADDR1_MICRO2440=(((phyaddr)>>22)<<21)|LOWER21BITS((phyaddr)>>1);
LCDSADDR2_MICRO2440=LOWER21BITS((phyaddr (LINEVAL_TFT_240320 1)*(HOZVAL_TFT_240320 1)*2)>>1);
LCDSADDR3_MICRO2440=(0<<11)|(LCD_XSIZE_TFT_240320*2/2);
TPAL_MICRO2440=0;
fb_base_addr=lcd_buffer_base_addr;
bpp=16;
xsize=240;
ysize=320;
LCDCON1_MICRO2440=LCDCON1_MICRO2440|(ENVID_ENABLE<<0);//使能屏幕输出
addr=fb_base_addr;// (10*xsize 100);
}
static ssize_t tft_write(struct file *file,char *buf,size_t count,loff_t *ppos)
{
unsigned long ret=0;
if((count pointer)<=(320*240*2))
{
ret=(unsigned long)copy_from_user(lcd_buffer_base_addr pointer,buf,count);//成功返回0,失败返回没有被COPY的字节数
if(ret==0)
{
pointer=0;
}
else
{
pointer=pointer (320*240*2)-ret;
}
return ret;
}
else
{
pointer=0;
return 0;
}
}
static int tft_open(struct inode *inode,struct file *file)
{
int ret;
ret=down_trylock(&lock);
if(ret==0)
{
tft_tb35_init();
return 0;
}
else
return -EBUSY;
}
static int tft_close(struct inode *inodep,struct file *file)
{
iounmap(base_addr);
iounmap(base_addr1);
iounmap(base_addr2);
iounmap(base_addr3);
iounmap(base_addr4);
clk_disable(tft_clock);
clk_put(tft_clock);
tft_clock=NULL;
up(&lock);//释放互斥锁
return 0;
}
static struct file_operations dev_fops={
.owner=THIS_MODULE,
.open=tft_open,
.release=tft_close,
.write=tft_write,
};
static struct miscdevice misc={
.name=DEVICE_NAME,
.minor=MISC_DYNAMIC_MINOR,
.fops=&dev_fops,
};
static int __init tft_micro2440_init(void)
{
int ret;
init_MUTEX(&lock);//初始化互斥锁
ret=misc_register(&misc); //注册混杂设备
return ret;
}
void __exit tft_micro2440_exit(void)
{
misc_deregister(&misc); //注销混杂设备
}
MODULE_LICENSE("Dual BSD/GPL");
MODULE_AUTHOR("xubin");
module_init(tft_micro2440_init);
module_exit(tft_micro2440_exit);
三。应用程序
#include
#include
#include
#include
#include
#include
#include "logo.h"
#define PWM_START 0x01
#define PWM_STOP 0x02
int main(int argc,char **argv)
{
unsigned long i=1;
unsigned long ret=0;
int fd;
unsigned long pointer=0;
unsigned long count_send=0;
fd=open("/dev/tft_tb35_micro2440_drv",O_RDWR);
if(fd<0)
{
printf("error\n");
exit(1);
}
pointer=0;
count_send=153600;
while(1)
{
ret=write(fd,gImage_logo+pointer,count_send);
printf("ret=%d\n",ret);
if(ret==0)
{
pointer=0;
count_send=153600;
}
else
{
pointer=pointer+153600-ret;
count_send=ret;
}
sleep(1);
}
close(fd);
return 0;
}
阅读(2335) | 评论(0) | 转发(0) |