之前一直使用OK6410A(256M內存+2GNand)(WinCE6.0系統),買了塊HDMI高清顯示,跟飛凌技術要了資料,按照所給的資料說明,對Eboot做了修改後,就可以正常使用HDMI高清顯示了。最近爲了節省幾十塊RMB,老闆決定更換板子使用128M內存+256MNand的板子,拿到手準備把高清部分加進去,可是發現Eboot不太一樣呀,編譯出錯。問了飛凌技術,人家告訴我他們沒有準備在這個板子上使用HDMI的資料說明。那怎麼辦呢,只能按照之前的資料來自己嘗試解決了。好在現在解決了,下面來看看是怎麼做的。
首先,應該修改main.c下的函數使其支持HDMI的選擇,因爲默認的沒有這個選項。主要是兩個函數:BOOL MainMenu(PBOOT_CFG pBootCfg)和void InitializeDisplay(void)函數。
在MainMenu函數中的下面一段switch-case中添加LCD_VGA1024_RGB選項,
switch(pBootCfg->ConfigFlags&LCD_TYPE_MASK)
{
case LCD_HUA350_RGB:
EdbgOutputDebugString ( "(320x240)\r\n");
break;
case LCD_HUA430_RGB:
EdbgOutputDebugString ( "(480x272)\r\n");
break;
case LCD_HUA560_RGB:
EdbgOutputDebugString ( "(640x480)\r\n");
break;
case LCD_QUN700_RGB:
EdbgOutputDebugString ( "(800x480)\r\n");
break;
case LCD_VGA800_RGB:
EdbgOutputDebugString ( "(800x600)\r\n");
break;
case LCD_VGA1024_RGB:
EdbgOutputDebugString ( "(1024x768)\r\n");
break;
default:
EdbgOutputDebugString ( "(unknown)\r\n");
break;
}
繼續查看這個函數,當選擇'S'即選擇設置LCD時,調用了SetLcd(pBootCfg);,在 SetLcd(PBOOT_CFG pBootCfg)函數下,修改如下
static void SetLcd(PBOOT_CFG pBootCfg)
{
USHORT InChar = 0;
EdbgOutputDebugString("\r\n");
EdbgOutputDebugString("0)3.5'LCD 320X240 \r\n");
EdbgOutputDebugString("1)4.3'LCD 480X272 \r\n");
EdbgOutputDebugString("2)5.6'LCD 640X480 \r\n");
EdbgOutputDebugString("3)7.0'LCD 800X480 \r\n");
EdbgOutputDebugString("4)VGA 800X600 \r\n");
EdbgOutputDebugString("5)HDMI 1024X768 \r\n");
EdbgOutputDebugString("\r\nSelect Lcd Resolution [0-5]: ");
while(!((InChar == 0x0d) || (InChar == 0x0a)))
{
InChar = OEMReadDebugByte();
if (InChar != OEM_DEBUG_COM_ERROR && InChar != OEM_DEBUG_READ_NODATA)
{
// If it's a number or a period, add it to the string.
//
if ((InChar >= '0' && InChar <= '5'))
{
OEMWriteDebugByte((BYTE)InChar);
pBootCfg->ConfigFlags&=~LCD_TYPE_MASK;
switch(InChar){
case '0':
pBootCfg->ConfigFlags|=LCD_HUA350_RGB;
break;
case '1':
pBootCfg->ConfigFlags|=LCD_HUA430_RGB;
break;
case '2':
pBootCfg->ConfigFlags|=LCD_HUA560_RGB;
break;
case '3':
pBootCfg->ConfigFlags|=LCD_QUN700_RGB;
break;
case '4':
pBootCfg->ConfigFlags|=LCD_VGA800_RGB;
break;
case '5':
pBootCfg->ConfigFlags|=LCD_VGA1024_RGB;
break;
default:
break;
}
break;
}
}
}
}
下面來修改 InitializeDisplay()函數,將其中選擇LCD模式的switch-case修改如下:
switch(g_pBootCfg->ConfigFlags&LCD_TYPE_MASK){
case LCD_HUA350_RGB:
LcdType = LDI_HUA350_RGB;
g_dwLcdWidth = 320;
g_dwLcdHeight = 240;
g_dwLcdBpp = 16;
break;
case LCD_HUA430_RGB:
LcdType = LDI_HUA430_RGB;
g_dwLcdWidth = 480;
g_dwLcdHeight = 272;
g_dwLcdBpp = 16;
break;
case LCD_HUA560_RGB:
LcdType = LDI_HUA560_RGB;
g_dwLcdWidth = 640;
g_dwLcdHeight = 480;
g_dwLcdBpp = 16;
break;
case LCD_QUN700_RGB:
LcdType = LDI_QUN700_RGB;
g_dwLcdWidth = 800;
g_dwLcdHeight = 480;
g_dwLcdBpp = 16;
break;
case LCD_VGA800_RGB:
LcdType = LDI_VGA800_RGB;
g_dwLcdWidth = 800;
g_dwLcdHeight = 600;
g_dwLcdBpp = 16;
break;
case LCD_VGA1024_RGB:
LcdType = LDI_VGA1024_RGB;
g_dwLcdWidth = 1024;
g_dwLcdHeight = 768;
g_dwLcdBpp = 16;
break;
default:
LcdType = LDI_HUA350_RGB;
g_dwLcdWidth = 320;
g_dwLcdHeight = 240;
g_dwLcdBpp = 16;
break;
}
到這裏就基本上修改完了,已經可以支持選擇HDMI了,但是僅僅是支持選擇,並不能真正實現HDMI高清顯示,考慮到在之前所給的資料中有個7033.lib還沒有使用,我比對了資料中的main.c 和 當前EBOOT中的 main.c,發現其調用了一個來自7033.lib的函數init_7033。於是仿照資料中的main.c做如下修改,主要是修改 InitializeVGA函數:
extern void init_7033(void);
//add by phantom
static void InitializeVGA(LDI_LCD_MODULE_TYPE LcdType)
{
unsigned int i;
//EdbgOutputDebugString("[Eboot] ++InitializeVGA LcdType %d\r\n",LcdType);
//IIC_Write //CH7026 write address = 0xec
if(LcdType==LDI_HUA560_RGB)
{
EdbgOutputDebugString("[Eboot] +++InitializeVGA 640X480()\r\n");
IIC_Open(2000);
for (i = 0; i < CH7026_REG_NUM_VGA_640; i++) {
if(!IIC_Write(0xEC, CH7026_REGS_VGA_640[i].subaddr, CH7026_REGS_VGA_640[i].value))
{
EdbgOutputDebugString("[Eboot] ---InitializeVGA ERROR!!!\r\n");
IIC_Close();
return;
}
}
IIC_Write(0xEC,0x4,0x0);
IIC_Close();
EdbgOutputDebugString("[Eboot] ---InitializeVGA 640X480()\r\n");
}
else if(LcdType==LDI_VGA800_RGB)
{
EdbgOutputDebugString("[Eboot] +++InitializeVGA 800X600()\r\n");
IIC_Open(2000);
for (i = 0; i < CH7026_REG_NUM_VGA_800; i++) {
if(!IIC_Write(0xEC, CH7026_REGS_VGA_800[i].subaddr, CH7026_REGS_VGA_800[i].value))
{
EdbgOutputDebugString("[Eboot] ---InitializeVGA ERROR!!!\r\n");
IIC_Close();
return;
}
}
IIC_Write(0xEC,0x4,0x0);
IIC_Close();
EdbgOutputDebugString("[Eboot] ---InitializeVGA 800X600()\r\n");
}
else if(LcdType==LDI_VGA1024_RGB)
{
/* add by alexlee*/
EdbgOutputDebugString("[Eboot] +++InitializeHDMI 1024X768()\r\n");
init_7033();
EdbgOutputDebugString("[Eboot] ---InitializeHDMI 1024X768()\r\n");
}
}
然後還有將7033.lib添加到Eboot的鏈接選項中,這個在資料中有說明,照做即可。完成這些工作後,還沒有最終完成,因爲此時在編譯Eboot時會出現編譯錯誤,這個主要是因爲在庫7033.lib中調用了一些函數,而這些函數還 沒有。比對了資料所給的usb.h、usb.c、ch7026.h,對當前Eboot下的文件進行了修改:
usb.h中添加:
BOOL IIC_Read(u8 cSlaveAddr,u8 cAddr,u8 *cData);
usb.c中添加:
void IIC_SetRead( u8 cSlaveAddr, u8 *pData, u32 uDataLen)
{
u32 uTmp2;
u32 uTmp3;
uTmp2= Input32(rIICSTAT0);
while(uTmp2&(1<<5)) // Wait until IIC bus is free.
uTmp2 = Input32(rIICSTAT0);
g_PcIIC_BUFFER = pData;
g_uIIC_PT = 0;
g_uIIC_DATALEN = uDataLen;
uTmp3 = Input32(rIICCON0);
uTmp3 |= (1<<7);
Outp32(rIICCON0,uTmp3); // Ack generation Enable
Outp32(rIICDS0,cSlaveAddr);
Outp32(rIICSTAT0,0xB0); // Master Rx Start.
}
BOOL IIC_Read(u8 cSlaveAddr,u8 cAddr,u8 *cData)
{
IIC_SetWrite( cSlaveAddr, &cAddr, 1); // following EEPROM random address access procedure
IIC_SetRead( cSlaveAddr, cData, 1);
IIC_Wait(); // Waiting for read complete.
}
將ch7026.h直接拷貝過來,覆蓋原有的ch7026.h文件,因爲資料中的這個文件中添加了一個CH7033_RegTable[][2]。
至此,就完成了修改工作了,此時重新編譯,然後生成映像。但是選擇了HDMI高清後,系統啓動到中間就停下來了,DNW上打印如下:
[Eboot] ++InitializeDisplay()
就是說在這個地方無法繼續往下執行了。我查找了這個語句,其是在InitializeDisplay()函數中打印的,進一步查找發現是下面的循環導致啓動中斷的:
for (i=0; i<g_dwLcdWidth*g_dwLcdHeight; i++)
*pFB++ = 0x0000;//0x001F; // Blue
這個循環是在初始LOGO中的,本身這個循環沒有什麼問題,我懷疑是否是由於越界導致的呢,看了下pFB指針,
unsigned short *pFB;
pFB = (unsigned short *)EBOOT_FRAMEBUFFER_UA_START;
進一步搜索EBOOT_FRAMEBUFFER_UA_START,在image_cfg.h中定義的,如下:
// Eboot Display Frame Buffer
// 2MB
#define EBOOT_FRAMEBUFFER_OFFSET (0x07F00000)
#define EBOOT_FRAMEBUFFER_PA_START (DRAM_BASE_PA_START+EBOOT_FRAMEBUFFER_OFFSET)
#define EBOOT_FRAMEBUFFER_UA_START (DRAM_BASE_UA_START+EBOOT_FRAMEBUFFER_OFFSET)
#define EBOOT_FRAMEBUFFER_SIZE (0x00100000)
將EBOOT_FRAMEBUFFER_OFFSET的值改爲0x07E00000。
再次重新編譯,生成映像。此時選擇HDMI高清就可以正常顯示了。所有工作也完成了,目前尚未發現有什麼異常,不過有待進一步觀察。。。。