Chinaunix首页 | 论坛 | 博客
  • 博客访问: 159792
  • 博文数量: 9
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 729
  • 用 户 组: 普通用户
  • 注册时间: 2013-05-08 14:00
文章分类

全部博文(9)

文章存档

2015年(1)

2014年(2)

2013年(6)

分类: LINUX

2013-07-19 11:36:18

                转载请声明出处:http://blog.chinaunix.net/uid/28764633

                经常在实验室坐着看一些理论性的书籍,好久没写过底层的驱动程序和应用程序了,写了下代码才发现有多痛苦,从unexpected identfication到SEGMENT SMASH 种种错误,代码其实很简单,写下来才发现有多辛苦。网上将FRAMBUFFER的内容很多,也进行了一些过参考,争取简洁一点介绍一下。
        一:LCD硬件工作原理篇以及驱动初始化的参数设置。
                首先介绍一下SC2410 LCD 的工作原理,首先LCD屏幕是由LCD控制器驱动的,下图简要说明一下,VIDEO发出对LCD屏的控制信号(起始帧,行刷新等),LPC是工作时钟信号,DMA负责为LCD显示读取内存数据。
                 
            简要说明:LCD根据VSYNC,HSYNC,VCLK不停的读取总线数据。
                1)VSYNC信号有效时,表示一个显示帧的开始。
                2)经历(VSPW+1+VBPSD+1)个无效行数据。
                3)随后发出连续的(LINEVAL+1)行的有效数据
                4)随后经历(VFPD+1)个无效行,VSYNC有效重复1)
                VSYNC是每帧开始的信号,同理对于每行开始的信号HSYNC也有本描述。
         ps:LCD屏的刷新方式,单扫,上下同时,等,还有具体的那种颜色模式,导致VD引脚输出的不同就不说了,比较琐碎。      
                关键在于我们在驱动初始化的时候将VSYNC,HSYNC,VCLK等信号的参数设置好,保证硬件能够正确工作,并且啊要将帧的内存地址(当然啦,你要在驱动程序里面要用KMALLOC来分配空间,具体的大小和你的屏幕的分辨率,像素位数有关,在SC2410里面支持16色的5551格式,565格式),这样DMA控制器就知道到哪里取数据啦。

                现在呢谈一下我们在驱动程序的void init fd_devices()要做的事情。这里就不给出源码了,大家理解了自己就会写的。
                CPU下的LCD相关寄存器说明以及寄存器设置:(简单说明,具体大家看我代码的参数,我们这个缓冲帧设置的是单缓冲,那么就用不到配置所有的寄存器配置)
                LCDCON1 控制寄存器,配置LCD时钟频率,显示模式,颜色位数等,最后一位是使能。
                                                    --ps  每次都看到有木有想死啊,想到前一阵子在FPGA上编写一个UART的时候,因为时钟时序,引脚的使能先后顺序做的泪牛满面
                LCDCON2 控制寄存器,配置LCD起始帧,长度等。
                LCDCON3 控制寄存器 ,配置LCD的行时序,一行包含的列数。
                LCDADDR1 FRAMBUFFER首地址
                LCDADDR2 FRAMBUFFER尾地址
                驱动程序设备初始化伪代码部分:
                        void init fd_devices()
                    {
                         rLCDCON1=0x00000178;      //配置成为16位颜色,TFT(真彩)模式;
                        rLCDCON2= 0x2077c241;     //行数为480;
                       rLCDCON3=0x017A7F0F;     //行宽为640;
                       rLCDADDR1=0x1904b000;      //FrameBuffer的首地址;
                       rLCDADDR2=0x00096000;    // FrameBuffer的尾地址;
                       rLCDADDR3= 0x00000300;   //虚屏行宽为640;
                         rLCDCON1 += 1;                        //使能LCD,开始显示;

                    }

                ps:大家请注意我们的驱动程序是不能直接访问IO空间的,必须通过映射IORMAP等方式来间接访问IO空间,伪代码中的寄存器变量名都是经过地址映射的。
            这里我们只是初始化了LCD设备,这只是工作的第一步,通过本节我们能够理解到LCD 的工作原理和 硬件初始化 。下一节我们将进入完整的驱动开发,我们将介绍内核对FRAMBUFFER的管理以及其他比较重要的结构体,和讨论一下LCD驱动编写的流程和步骤。


            

                       
            
            
                

阅读(2631) | 评论(0) | 转发(1) |
给主人留下些什么吧!~~