📄 hio.c
字号:
#include "winav.h"
#include "ctkav.h"
#include "ctkav_mcu.h"
#include "hio.h"
#ifdef SUPPORT_I2C
VOID _Delay_I2C(void);
VOID _IIC_START (PI2C_CONFIG pConfig);
VOID _IIC_TxByte (PI2C_CONFIG pConfig, BYTE bValue);BYTE _IIC_RxByte (PI2C_CONFIG pConfig);BYTE _IIC_GetACK (PI2C_CONFIG pConfig);VOID _IIC_SetACK (PI2C_CONFIG pConfig);VOID _IIC_STOP (PI2C_CONFIG pConfig);VOID _I2C_Set_SDAT_HIGH(PI2C_CONFIG pConfig);VOID _I2C_Set_SCLK_HIGH(PI2C_CONFIG pConfig);VOID _I2C_Set_SDAT_LOW(PI2C_CONFIG pConfig);VOID _I2C_Set_SCLK_LOW(PI2C_CONFIG pConfig);BYTE _I2C_Get_SDAT(PI2C_CONFIG pConfig);
#endif //#ifdef SUPPORT_I2C
#ifdef ENABLE_PANEL_KEYSCAN
extern BYTE __icVFDnow;
#endif // #ifdef ENABLE_PANEL_KEYSCAN
// Define GPB register address -- LLY2.01
// LLY2.56, split GPB output data control to two different register,
// ie. one is for set 1, another is for clear 0
#ifdef CT909G_IC_SYSTEM
#define REG_SERVO_GPB_SETDATA (*(volatile DWORD *)(0x80002480+(DWORD)0x30*4))
#define REG_SERVO_GPB_CLEARDATA (*(volatile DWORD *)(0x80002480+(DWORD)0x32*4))
#else // #ifdef CT909G_IC_SYSTEM
#define REG_SERVO_GPB_OUTDATA (*(volatile DWORD *)(0x80002480+(DWORD)0x30*4))
#endif // #ifdef CT909G_IC_SYSTEM
#define REG_SERVO_GPB_INDATA (*(volatile DWORD *)(0x80002480+(DWORD)0x31*4))
#define REG_SERVO_GPB_IO_DIR_CONTROL (*(volatile DWORD *)(0x80002480+(DWORD)0x33*4))
#define REG_SERVO_GPB_FUNC_SEL (*(volatile DWORD *)(0x80002480+(DWORD)0x36*4))
// LLY2.18, define a mutex for I2C and Expand GPIO procedure share same pin issue
MUTEX_T __mutexI2CReady;
#ifdef SW_EXPAND_GPIO
// LLY2.16 create
// LLY2.20, modify the procedure, since it will call lower level API to scan all key once time
// ************************************************************************************
// Function : _SW_Expand_GPI
// Description : Using S/W mechanism to do expand GPI feature
// Arguments : dwPort, specify the desired port, index from '0'
// Return : The port status
// ************************************************************************************
BYTE _SW_Expand_GPI(DWORD dwPort)
{
DWORD dwDesiredPort;
// LLY2.60, add error protection base on supporting
#ifdef NO_KEY_DETECT_0
if(dwPort < 8)
{
DBG_Printf(DBG_THREAD_CHEERDVD, DBG_INFO_PRINTF, "Err: not support key detect0, port: %lx\n", dwPort);
return FALSE;
}
#endif // #ifdef NO_KEY_DETECT_0
#ifdef NO_KEY_DETECT_1
if(dwPort >= 8)
{
DBG_Printf(DBG_THREAD_CHEERDVD, DBG_INFO_PRINTF, "Err: not support key detect1, port: %lx\n", dwPort);
return FALSE;
}
#endif // #ifdef NO_KEY_DETECT_1
// Calculate the desired port position.
dwDesiredPort = (1<<dwPort);
// Return the status of desired port
if(HAL_Read_ExpGPI() & dwDesiredPort)
{
return TRUE;
}
else
{
return FALSE;
}
}
DWORD __dwExpGPOVal=0;
// LLY2.16 create
// ************************************************************************************
// Function : _SW_Expand_GPO
// Description : Using S/W mechanism to do expand GPO feature
// Arguments : dwPort, specify the desired port
// Return : The port status
// ************************************************************************************
void _SW_Expand_GPO(DWORD dwPort, BYTE bValue)
{
BYTE bLatchVal;
BYTE bIdx;
BYTE bShiftBit;
DWORD dwSaveInt;
// LLY2.60, add error protection while don't support latch D1
#ifdef NO_LATCH_D0
if(dwPort < 8)
{
DBG_Printf(DBG_THREAD_CHEERDVD, DBG_INFO_PRINTF, "Err: not support latch D0, port: %lx\n", dwPort);
return;
}
#endif // #ifdef NO_LATCH_D0
#ifdef NO_LATCH_D1
if(dwPort >= 8)
{
DBG_Printf(DBG_THREAD_CHEERDVD, DBG_INFO_PRINTF, "Err: not support latch D1, port: %lx\n", dwPort);
return;
}
#endif // #ifdef NO_LATCH_D1
OS_DISABLE_INTERRUPTS(dwSaveInt);
// Step 1: Set desired value to desired port
if(bValue)
{
__dwExpGPOVal |= (1<<dwPort);
}
else
{
__dwExpGPOVal &= ~(1<<dwPort);
}
// Step 2: Calculate desired latch value (only 8 bit)
if(dwPort>=8) // port 8 ~ 15
{
bLatchVal = (BYTE)(__dwExpGPOVal>>8);
}
else // port 0 ~ 7
{
bLatchVal = (BYTE)(__dwExpGPOVal & 0xFF);
}
// Step 3: Set shift bit w/ 0x80 since bit[7] shift first
bShiftBit=0x80; // enable bit[7] as 1 first
// Step 4: Generate clock and data one by one
for(bIdx=0; bIdx<8; bIdx++)
{
if(bLatchVal & bShiftBit)
{
_KS_DAT_HI;
}
else
{
_KS_DAT_LO;
}
// Shift Register (164) is rising edge trigger, so clock is low --> high
_KS_CLK_LO;
_KS_CLK_HI;
// shift right 1 bit for next data
bShiftBit >>= 1;
}
// Step 5: Set latch signal as high since 373 register is high level trigger
// And, set the signal as low to release the latch
if(dwPort>=8) // port 8 ~ 15
{
_KS_LATCH1_HI;
_KS_LATCH1_LO;
}
else // port 0 ~ 7
{
_KS_LATCH0_HI;
_KS_LATCH0_LO;
}
OS_RESTORE_INTERRUPTS(dwSaveInt);
}
#endif // #ifdef SW_EXPAND_GPIO
// LLY2.20 create,
// **************************************************************************************
// Function : HAL_Read_ExpGPI
// Description : Read back Expand GPI all port status
// Arguments : None
// Return : All port status from expand GPI
// **************************************************************************************
DWORD HAL_Read_ExpGPI(void)
{
#ifdef ENABLE_EXPAND_GPIO
return (REG_PLAT_PANEL_KD);
#endif // #ifdef ENABLE_EXPAND_GPIO
#ifdef SW_EXPAND_GPIO
BYTE bIdx;
DWORD dwGPIValue=0;
DWORD dwSaveInt;
BYTE bDelay;
// Disable interrupt first since following key scan action can't be interrupt.
OS_DISABLE_INTERRUPTS(dwSaveInt);
#ifdef ACTIVE_LOW
// Step 0: initial first 7 port w/ high signal, ie. port 0 ~ 6, or port 8 ~ 14
_KS_DAT_HI;
for(bIdx=0; bIdx<7; bIdx++)
{
// Shift Register (164) is rising edge trigger, so clock is low --> high
_KS_CLK_LO;
_KS_CLK_HI;
}
// Step 2: output low signal (x1) + low/ high clock
// then output high signal later to generate a low pulse
_KS_DAT_LO;
_KS_CLK_LO;
_KS_CLK_HI;
_KS_DAT_HI;
// Step 3: Read back the key detect 0/ 1 value for port 0 and 8
// LLY2.60, add protection: only do operation while enable define.
//dwGPIValue = ((DWORD)(!_KS_DET0_READ)) + (((DWORD)(!_KS_DET1_READ)) <<8);
#ifndef NO_KEY_DETECT_0
dwGPIValue |= ((DWORD)(!_KS_DET0_READ));
#endif // #ifndef NO_KEY_DETECT_0
#ifndef NO_KEY_DETECT_1
dwGPIValue |= (((DWORD)(!_KS_DET1_READ)) <<8);
#endif // #ifndef NO_KEY_DETECT_1
// Step 4: Loop 7 time to generate low/ high clock to shift low pulse from port 1~7 or 9~ 15
// And, read back the key detect 0/ 1 value
for(bIdx=1; bIdx<8; bIdx++)
{
// Must delay a while before next clock pulse
// Since RC charge/ dis-charge effect for data pin ready.
for(bDelay = 0;bDelay<128;bDelay++)
{
NOP;
}
_KS_CLK_LO;
_KS_CLK_HI;
// LLY2.60, add protection: only do operation while enable define.
//dwGPIValue |= (((DWORD)(!_KS_DET0_READ))<<bIdx) + (((DWORD)(!_KS_DET1_READ))<<(bIdx+8));
#ifndef NO_KEY_DETECT_0
dwGPIValue |= (((DWORD)(!_KS_DET0_READ))<<bIdx);
#endif // #ifndef NO_KEY_DETECT_0
#ifndef NO_KEY_DETECT_1
dwGPIValue |= (((DWORD)(!_KS_DET1_READ))<<(bIdx+8));
#endif // #ifndef NO_KEY_DETECT_1
}
#else // #ifdef ACTIVE_LOW
// Step 0: initial firt 7 port w/ low signal, ie port 0 ~ 6 or port 8 ~ 14
_KS_DAT_LO;
for(bIdx=0; bIdx<7; bIdx++)
{
// Shift Register (164) is rising edge trigger, so clock is low --> high
_KS_CLK_LO;
_KS_CLK_HI;
}
// Step 2: output high signal (x1) + low/ high clock
// then output low signal later to generate a high pulse
_KS_DAT_HI;
_KS_CLK_LO;
_KS_CLK_HI;
_KS_DAT_LO;
// Step 3: Read back the key detect 0/ 1 value for port 0 and 8
// LLY2.60, add protection: only do operation while enable define.
//dwGPIValue = ((DWORD)_KS_DET0_READ) + (((DWORD)_KS_DET1_READ) <<8);
#ifndef NO_KEY_DETECT_0
dwGPIValue |= ((DWORD)_KS_DET0_READ);
#endif // #ifndef NO_KEY_DETECT_0
#ifndef NO_KEY_DETECT_1
dwGPIValue |= (((DWORD)_KS_DET1_READ) <<8);
#endif // #ifndef NO_KEY_DETECT_1
// Step 4: Loop 7 time to generate low/ high clock to shift low pulse from port 1 ~ 7 or 9 ~ 15
// And, read back the key detect 0/ 1 value
for(bIdx=1; bIdx<8; bIdx++)
{
// Must delay a while before next clock pulse
// Since RC charge/ dis-charge effect for data pin ready.
for(bDelay = 0;bDelay<128;bDelay++)
{
NOP;
}
_KS_CLK_LO;
_KS_CLK_HI;
// LLY2.60, add protection: only do operation while enable define.
//dwGPIValue |= (((DWORD)_KS_DET0_READ)<<bIdx) + (((DWORD)_KS_DET1_READ)<<(bIdx+8));
#ifndef NO_KEY_DETECT_0
dwGPIValue |= (((DWORD)_KS_DET0_READ)<<bIdx);
#endif // #ifndef NO_KEY_DETECT_0
#ifndef NO_KEY_DETECT_1
dwGPIValue |= (((DWORD)_KS_DET1_READ)<<(bIdx+8));
#endif // #ifndef NO_KEY_DETECT_1
}
#endif // #ifdef ACTIVE_LOW
// LLY2.50, Porting Jeff's code to send clock low/ high signal again
// to reset 74138 for All ping = High output
// If not , the will always keep KS_DET0/1 pin as low,
// and cause other pin shared it will work abnormal
_KS_CLK_LO;
_KS_CLK_HI;
OS_RESTORE_INTERRUPTS(dwSaveInt);
return dwGPIValue;
#endif // #ifdef SW_EXPAND_GPIO
return FALSE;
}
// **********************************************************************************************
// Function : HAL_ReadGPIO
// Description : Read the value from the desired GPA port
// Arguments : bGroup: specify the GPIO group
// dwPort: port #
// Return : 1: High
// 0: Low
// Notice : Must disable interrupt first since GPIO maybe accessed by different thread
// *********************************************************************************************
// LLY2.13, modify the procedure and add expand GPIO code
// LLY2.15, modify the procedure for GPIO CDEF group
// LLY2.50, modify the procedure to support extra CT909P GPIO group
BYTE HAL_ReadGPIO(BYTE bGroup, DWORD dwPort)
{
DWORD dwSaveInt;
// Used to keep desired port position, one port -> one position
DWORD dwDesiredPort;
#ifdef CT909R_IC_SYSTEM
if(bGroup == GPIO_F)
{
DBG_Printf(DBG_THREAD_CHEERDVD, DBG_INFO_PRINTF, "Err: Not implement GPIO group\n");
return FALSE;
}
#endif // #ifndef CT909P_IC_SYSTEM
// LLT2.77, remove the error protection before disable interrupt action.
#ifdef CT909P_IC_SYSTEM
if(bGroup == GPIO_B)
{
if(dwPort >= 6)
{
DBG_Printf(DBG_THREAD_CHEERDVD, DBG_INFO_PRINTF, "Err: Not supported GPB port\n");
return FALSE;
}
}
#endif // #ifdef CT909P_IC_SYSTEM
if(bGroup == GPIO_EXP)
{
// LLY2.16, go S/W Expand GPIO path
#ifdef SW_EXPAND_GPIO
return (_SW_Expand_GPI(dwPort));
#endif // #ifdef SW_EXPAND_GPIO
}
// Shift the desired port to final position first
dwDesiredPort = (1<<dwPort);
// GPCDE @ same register for CT909R
#ifdef CT909R_IC_SYSTEM
// Shift left again for GPIO CDE, since they shared the same register
if(bGroup==GPIO_D)
{
// Shift left 8 bit since GPIO D @ bit[15:8] first
dwDesiredPort = (dwDesiredPort << 8);
}
else if(bGroup==GPIO_E)
{
// Shift left 16 bit since GPIO E @ bit [24:16] first
dwDesiredPort = (dwDesiredPort << 16);
}
#endif // #ifdef CT909R_IC_SYSTEM
// Disable interrupt first
OS_DISABLE_INTERRUPTS(dwSaveInt);
// Set GPIO as input mode
if(bGroup==GPIO_A)
{
// LLY2.50, config GPA Mux selection register for using GPA as GPIO @ CT909P
#ifdef CT909P_IC_SYSTEM
if(dwPort==0)
{
// GPAMux[0]=1, GPAMux[2:1]=0
REG_PLAT_GPA_MUX &= ~(0x7L);
REG_PLAT_GPA_MUX |= 0x1L;
}
else if(dwPort==1)
{
// GPAMux[3]=1, GPAMux[5:4]=0
REG_PLAT_GPA_MUX &= ~(0x7L<<3);
REG_PLAT_GPA_MUX |= (0x1L<<3);
}
else if(dwPort==2)
{
// GPAMux[6]=1, GPAMux[8:7]=0
REG_PLAT_GPA_MUX &= ~(0x7L<<6);
REG_PLAT_GPA_MUX |= (0x1L<<6);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -