关于spi接口的lcd初始化

本文记录了作者使用S3C2440开发板通过SPI接口点亮LCD屏幕的过程,包括bootloader、eBoot及Wince内核阶段的调试心得,特别讨论了虚拟地址使用和内存管理等问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

 今天终于把spi接口的屏幕给点亮了,带着疑问,小小总结下。
    我用的是s3c2440,由飞凌提供的bootloader。这段时间一直在看飞凌的代码是如何处理lcd屏幕的。从整个代码中可以看出,飞凌只在bootloader中初始化了lcd屏幕,eboot以及wince驱动中都没有初始化,这让我一开始以为,我换了屏幕是不是也只要修改bootloader中的代码就行了。现实总是比想像中的复杂,在我修改了bootloader中的初始化后,成功将lcd屏幕点亮,能维持到eboot,但是往wince内核跳转的时候,屏幕就熄灭了。这是怎么回事?
    由于飞凌的原屏幕没有使用spi接口,而现在的屏幕需要使用spi初始化寄存器,我想是不是在wince的display驱动中再见添加initdisplay就可以点亮了呢,事实证明,我又单纯了!当然在这期间也遇到了很多问题,比如wince虚拟地址的使用,以及内存溢出的处理,c语言严重不过关啊!关于spi接口的lcd初始化最后使用笨办法也算是勉强过了,但是屏幕就是不亮。哪里出现问题了呢?
    后来想到之前还用过2416的开发板,就试着去看了它的eboot,发现那款开发板的lcd初始化是在eboot中,再次移植,把初始化搬过来,根据飞凌代码的注释,放到了fmd之前,依然没亮。再看看2416,放在了跳转前,好,模仿一下,还真是,到wince中亮了,那个激动啊,下周一勉强可以交差了!
   当然,也是勉强,问题还是有的!现在我还需要:
   1.将显示由320*240改成240*320,这个简单,之前做过;
   2.修改寄存器参数,主要是现实画面有点花,应该是一些参数没有设置好;
   3.wince画面好像是镜像显示的,不知道前面两个解决了,第三个能不能解决!
   4.触摸屏没反应!这个在老屏幕上也存在。以后再说。
   还有一些疑问,
   1.fmd到底是干什么的?里面涉及到spi三条线了?为什么前后互换一下就不亮了!
   2.我看有些lcd屏幕好像是在wince初始化的,为什么我在wince驱动中初始化不行呢?
   3.VirtualAlloc,VirtualCopy,MmMapIoSpace,还有OALPAtoVA这些和虚拟地址有关的函数有待研究。
  下面的一段代码是屏幕的ic驱动的初始化,Driver IC:HX8347-I,主要问题是多次申请内存,然后绑定虚拟地址,最后烧进板子中出现错误,我的理解应该是内存不够,不知道是不是这个原因。c语言不过关,也不知道怎么在全局申请一段地址,或者是释放那部分内存,这段代码折磨了我很长时间,以后再研究吧


void LCDICINIT(void)
  {
    LCDSPI_InitCMD(0xE4);LCDSPI_InitDAT(0x02); //
    LCDSPI_InitCMD(0xE5);LCDSPI_InitDAT(0x10); //
    LCDSPI_InitCMD(0xE6);LCDSPI_InitDAT(0x10); //
    LCDSPI_InitCMD(0xE7);LCDSPI_InitDAT(0x02); // 
//Gamma 2.2 Setting 
    LCDSPI_InitCMD(0x40);LCDSPI_InitDAT(0x01); //
    LCDSPI_InitCMD(0x41);LCDSPI_InitDAT(0x15); //
    LCDSPI_InitCMD(0x42);LCDSPI_InitDAT(0x14); //
    LCDSPI_InitCMD(0x43);LCDSPI_InitDAT(0x30); //
    LCDSPI_InitCMD(0x44);LCDSPI_InitDAT(0x30); //
    LCDSPI_InitCMD(0x45);LCDSPI_InitDAT(0x3C); //
    LCDSPI_InitCMD(0x46);LCDSPI_InitDAT(0x10); //
    LCDSPI_InitCMD(0x47);LCDSPI_InitDAT(0x6E); //
    LCDSPI_InitCMD(0x48);LCDSPI_InitDAT(0x07); //
    LCDSPI_InitCMD(0x49);LCDSPI_InitDAT(0x0F); //
    LCDSPI_InitCMD(0x4A);LCDSPI_InitDAT(0x12); //
    LCDSPI_InitCMD(0x4B);LCDSPI_InitDAT(0x12); //
    LCDSPI_InitCMD(0x4C);LCDSPI_InitDAT(0x19); //
    LCDSPI_InitCMD(0x50);LCDSPI_InitDAT(0x03); //
    LCDSPI_InitCMD(0x51);LCDSPI_InitDAT(0x0F); //
    LCDSPI_InitCMD(0x52);LCDSPI_InitDAT(0x0F); //
    LCDSPI_InitCMD(0x53);LCDSPI_InitDAT(0x2B); //
    LCDSPI_InitCMD(0x54);LCDSPI_InitDAT(0x2A); //
    LCDSPI_InitCMD(0x55);LCDSPI_InitDAT(0x3E); //
    LCDSPI_InitCMD(0x56);LCDSPI_InitDAT(0x11); //
    LCDSPI_InitCMD(0x57);LCDSPI_InitDAT(0x6F); //
    LCDSPI_InitCMD(0x58);LCDSPI_InitDAT(0x06); //
    LCDSPI_InitCMD(0x59);LCDSPI_InitDAT(0x0D); //
    LCDSPI_InitCMD(0x5A);LCDSPI_InitDAT(0x0D); //
    LCDSPI_InitCMD(0x5B);LCDSPI_InitDAT(0x10); //
    LCDSPI_InitCMD(0x5C);LCDSPI_InitDAT(0x18); //
    LCDSPI_InitCMD(0x5D);LCDSPI_InitDAT(0xCC); //

//Power Voltage Setting
    LCDSPI_InitCMD(0x1B);LCDSPI_InitDAT(0x1B);  //VRH=4.65V
    LCDSPI_InitCMD(0x1A);LCDSPI_InitDAT(0x01);  //BT (VGH~15V);LCDSPI_InitDAT(VGL~-10V);LCDSPI_InitDAT(DDVDH~5V)
    LCDSPI_InitCMD(0x24);LCDSPI_InitDAT(0x40);  //VMH(VCOM High voltage ~3.2V)
    LCDSPI_InitCMD(0x25);LCDSPI_InitDAT(0x54);  //VML(VCOM Low voltage -1.2V)

    LCDSPI_InitCMD(0x23);LCDSPI_InitDAT(0xA8);  //for Flicker adjust //can reload from OTP

//240x320 window setting
LCDSPI_InitCMD(0x0002);LCDSPI_InitDAT(0x0000);
LCDSPI_InitCMD(0x0003);LCDSPI_InitDAT(0x0000);
LCDSPI_InitCMD(0x0004);LCDSPI_InitDAT(0x0000);
LCDSPI_InitCMD(0x0005);LCDSPI_InitDAT(0x00EF);
LCDSPI_InitCMD(0x0006);LCDSPI_InitDAT(0x0000);
LCDSPI_InitCMD(0x0007);LCDSPI_InitDAT(0x0000);
LCDSPI_InitCMD(0x0008);LCDSPI_InitDAT(0x0001);
LCDSPI_InitCMD(0x0009);LCDSPI_InitDAT(0x003F);



//Power on Setting
    LCDSPI_InitCMD(0x18);LCDSPI_InitDAT(0x88);  //I/P_RADJ);LCDSPI_InitDAT(N/P_RADJ);LCDSPI_InitDAT( Normal mode 60Hz
    LCDSPI_InitCMD(0x19);LCDSPI_InitDAT(0x01);  //OSC_EN='1');LCDSPI_InitDAT( start Osc
    LCDSPI_InitCMD(0x01);LCDSPI_InitDAT(0x00);  //DP_STB='0');LCDSPI_InitDAT( out deep sleep
    LCDSPI_InitCMD(0x1F);LCDSPI_InitDAT(0x88);// GAS=1);LCDSPI_InitDAT( VOMG=00);LCDSPI_InitDAT( PON=0);LCDSPI_InitDAT( DK=1);LCDSPI_InitDAT( XDK=0);LCDSPI_InitDAT( DVDH_TRI=0);LCDSPI_InitDAT( STB=0
    Delayms(5);
    LCDSPI_InitCMD(0x1F);LCDSPI_InitDAT(0x80);// GAS=1);LCDSPI_InitDAT( VOMG=00);LCDSPI_InitDAT( PON=0);LCDSPI_InitDAT( DK=0);LCDSPI_InitDAT( XDK=0);LCDSPI_InitDAT( DVDH_TRI=0);LCDSPI_InitDAT( STB=0
    Delayms(5);
    LCDSPI_InitCMD(0x1F);LCDSPI_InitDAT(0x90);// GAS=1);LCDSPI_InitDAT( VOMG=00);LCDSPI_InitDAT( PON=1);LCDSPI_InitDAT( DK=0);LCDSPI_InitDAT( XDK=0);LCDSPI_InitDAT( DVDH_TRI=0);LCDSPI_InitDAT( STB=0
    Delayms(5);
    LCDSPI_InitCMD(0x1F);LCDSPI_InitDAT(0xD4);// GAS=1);LCDSPI_InitDAT( VOMG=10);LCDSPI_InitDAT( PON=1);LCDSPI_InitDAT( DK=0);LCDSPI_InitDAT( XDK=0);LCDSPI_InitDAT( DDVDH_TRI=0);LCDSPI_InitDAT( STB=0
    Delayms(5);

//262k/65k color selection
//LCDSPI_InitCMD(0x17);LCDSPI_InitDAT(0x66);  //default 0x60 262k color // 0x50 65k color
    LCDSPI_InitCMD(0x17);LCDSPI_InitDAT(0x60); //changed by ycj
    LCDSPI_InitCMD(0x31);LCDSPI_InitDAT(0x02);
    Delayms(20);//0x0e 
    LCDSPI_InitCMD(0x32);LCDSPI_InitDAT(0x06);//0x0e 
    LCDSPI_InitCMD(0x33);LCDSPI_InitDAT(0x02); 
    LCDSPI_InitCMD(0x34);LCDSPI_InitDAT(0x02); 

//Display ON Setting
    LCDSPI_InitCMD(0x28);LCDSPI_InitDAT(0x38);   //GON=1);LCDSPI_InitDAT( DTE=1);LCDSPI_InitDAT( D=1000
    Delayms(40);
    LCDSPI_InitCMD(0x28);LCDSPI_InitDAT(0x3C);   //GON=1);LCDSPI_InitDAT( DTE=1);LCDSPI_InitDAT( D=1100 
    Delayms(40);
    LCDSPI_InitCMD(0x36);LCDSPI_InitDAT(0x03); ////SS_P);LCDSPI_InitDAT( GS_P);LCDSPI_InitDAT(REV_P);LCDSPI_InitDAT(BGR_P)

// add ycj
    LCDSPI_InitCMD(0x0090);LCDSPI_InitDAT(0x007F); 
    Delayms(40);
    LCDSPI_InitCMD(0x0026);LCDSPI_InitDAT(0x0004); 
    Delayms(40);
    LCDSPI_InitCMD(0x0026);LCDSPI_InitDAT(0x0024); 
    Delayms(40);
    LCDSPI_InitCMD(0x0026);LCDSPI_InitDAT(0x002C); 
    Delayms(40);
    LCDSPI_InitCMD(0x0026);LCDSPI_InitDAT(0x003C); 
    Delayms(40);

//Lcd_EnvidOnOff(1);

    //s2440LCD->LCDCON1 |= 1; // Enable LCD output

// RETAILMSG(1, (TEXT("--S3C2440DISP::InitDisplay done \r\n")));

}
 void LCDSPI_InitCMD( unsigned short data)   //LCDVF0=CS; LCDVF1=SDI; LCDVF2=SCK
{
unsigned short i,MB=0X7400;
// MB=MB|data;
CS(0);
Delayus(10);
SCLK(1);
SDI(1);
//Delayus(100);
//SCLK(1);
Delayus(100);//Delayus(120);

for(i=0;i<8;i++)
 {
SCLK(0);  
  if(MB&0x8000)
SDI(1);    
  else
SDI(0);
 
Delayus(100);
SCLK(1);
Delayus(100);//Delayus(120);
//SCLK(0);
  MB<<=1;
 }

    MB=data;
for(i=0;i<8;i++)
 {
SCLK(0);  
  if(MB&0x80)
SDI(1);    
  else
SDI(0);
 
Delayus(100);
SCLK(1);
Delayus(100);//Delayus(120);
//SCLK(0);
  MB<<=1;
 }
CS(1);
}


 void LCDSPI_InitDAT(unsigned short data)
{
unsigned short i,MB=0x7600;
// MB=MB|data;
CS(0);
Delayus(10);
SCLK(1);
SDI(1);
//Delayus(100);
//SCLK(1);
Delayus(100);//Delayus(120);


for(i=0;i<8;i++)
 {
SCLK(0);  
  if(MB&0x8000)
SDI(1);    
  else
SDI(0);
 
Delayus(100);
SCLK(1);
Delayus(100);//Delayus(120);
//SCLK(0);
   MB<<=1;
 }

 MB=data;
for(i=0;i<8;i++)
 {
SCLK(0);  
  if(MB&0x80)
SDI(1);    
  else
SDI(0);
 
Delayus(100);
SCLK(1);
Delayus(100);//Delayus(120);
//SCLK(0);
  MB<<=1;
 }
CS(1);
}


 

 void CS( unsigned short flag)
{//GPG3
volatile S3C2440A_IOPORT_REG *s2440IOP=NULL;
    s2440IOP = (volatile S3C2440A_IOPORT_REG *) VirtualAlloc(0,sizeof(S3C2440A_IOPORT_REG),MEM_RESERVE, PAGE_NOACCESS);
if(s2440IOP == NULL) {
RETAILMSG(1,(TEXT("For s2440IOP: VirtualAlloc 2 failed!\r\n")));
}
else {
if(!VirtualCopy((PVOID)s2440IOP,(PVOID)(S3C2440A_BASE_REG_PA_IOPORT >> 8),sizeof(S3C2440A_IOPORT_REG),PAGE_PHYSICAL | PAGE_READWRITE | PAGE_NOCACHE )) {
RETAILMSG(1,(TEXT("For s2440IOP: VirtualCopy 2 failed!\r\n")));
}
}
//volatile S3C2440A_IOPORT_REG *s2440IOP = (S3C2440A_IOPORT_REG *)OALPAtoVA(S3C2440A_BASE_REG_PA_IOPORT, FALSE);
if(~((s2440IOP->GPGUP)&(1<<7)))
s2440IOP->GPGUP=(s2440IOP->GPGUP)&(~(1<<3))|(1<<3); // Pull-up disable
if(flag)
{
  s2440IOP->GPGDAT=((s2440IOP->GPGDAT)&(~(1<<3)))|(1<<3);

}
else
{
s2440IOP->GPGDAT=(s2440IOP->GPGDAT)&(~(1<<3));
}
if((~((s2440IOP->GPGCON)&(0x3<<6)))!=(1<<6))
    s2440IOP->GPGCON=(s2440IOP->GPGCON)&(~(0x3<<6))|(1<<6);   //output enable 1
}
static void SCLK( unsigned short flag)
{//GPG7
//volatile S3C2440A_IOPORT_REG *s2440IOP = (S3C2440A_IOPORT_REG *)OALPAtoVA(S3C2440A_BASE_REG_PA_IOPORT, FALSE);
 volatile S3C2440A_IOPORT_REG *s2440IOP=NULL;
 s2440IOP = (volatile S3C2440A_IOPORT_REG *) VirtualAlloc(0,sizeof(S3C2440A_IOPORT_REG),MEM_RESERVE, PAGE_NOACCESS);
if(s2440IOP == NULL) {
RETAILMSG(1,(TEXT("For s2440IOP: VirtualAlloc 3 failed!\r\n")));
}
else {
if(!VirtualCopy((PVOID)s2440IOP,(PVOID)(S3C2440A_BASE_REG_PA_IOPORT >> 8),sizeof(S3C2440A_IOPORT_REG),PAGE_PHYSICAL | PAGE_READWRITE | PAGE_NOCACHE )) {
RETAILMSG(1,(TEXT("For s2440IOP: VirtualCopy 3 failed!\r\n")));
}
}
if(~((s2440IOP->GPGUP)&(1<<7)))
s2440IOP->GPGUP=(s2440IOP->GPGUP)&(~(1<<7))|(1<<7); // Pull-up disable

if(flag)
{
  s2440IOP->GPGDAT=(s2440IOP->GPGDAT)&(~(1<<7))|(1<<7);

}
else
{
(s2440IOP->GPGDAT)=(s2440IOP->GPGDAT)&(~(1<<7));
}
if((~((s2440IOP->GPGCON)&(0x3<<14)))!=(1<<14))
    s2440IOP->GPGCON=(s2440IOP->GPGCON)&(~(0x3<<14))|(1<<14); //output enable 1
}
static void SDI( unsigned short flag)
{//GPG6
//volatile S3C2440A_IOPORT_REG *s2440IOP = (S3C2440A_IOPORT_REG *)OALPAtoVA(S3C2440A_BASE_REG_PA_IOPORT, FALSE);
 volatile S3C2440A_IOPORT_REG *s2440IOP=NULL;
  s2440IOP = (volatile S3C2440A_IOPORT_REG *) VirtualAlloc(0,sizeof(S3C2440A_IOPORT_REG),MEM_RESERVE, PAGE_NOACCESS);
if(s2440IOP == NULL) {
RETAILMSG(1,(TEXT("For s2440IOP: VirtualAlloc 4 failed!\r\n")));
}
else {
if(!VirtualCopy((PVOID)s2440IOP,(PVOID)(S3C2440A_BASE_REG_PA_IOPORT >> 8),sizeof(S3C2440A_IOPORT_REG),PAGE_PHYSICAL | PAGE_READWRITE | PAGE_NOCACHE )) {
RETAILMSG(1,(TEXT("For s2440IOP: VirtualCopy 4 failed!\r\n")));
}
}
if(~((s2440IOP->GPGUP)&(1<<6)))
s2440IOP->GPGUP=(s2440IOP->GPGUP)&(~(1<<6))|(1<<6); // Pull-up disable

if(flag)
{
  s2440IOP->GPGDAT=(s2440IOP->GPGDAT)&(~(1<<6))|(1<<6);

}
else
{
s2440IOP->GPGDAT=(s2440IOP->GPGDAT)&(~(1<<6));
}
if((~((s2440IOP->GPGCON)&(0x3<<12)))!=(1<<12))
    s2440IOP->GPGCON=(s2440IOP->GPGCON)&(~(3<<12))|(1<<12); //output enable 1
}


 void Delayus( int cnt)
{
int i,j;
for(i=0;i<cnt;i++)
{
for(j=0;j<0x1;j++)
{
j++;
}
}
}

 void Delayms( int cnt)
{
int i;
for(i=0;i<cnt;i++)
{
Delayus(100);
}
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值